achille
achille

Reputation: 113

Remove 4 chars before the last char with sed (or awk)

I would like to remove the 4 chars before the last char.

Input:

abc2a982
e1kei9e5bc5
e1edeaww58476

Expected output:

abc2
e1kei95
e1edeaww6

So far I have tried:

cat file | while read line; do echo $line | sed 's/.\{4}$\1/';done

I guess there should be something else instead of \1.

Upvotes: 2

Views: 334

Answers (2)

ghoti
ghoti

Reputation: 46866

If you had the urge to do this with bash alone, and avoid using sed, you could use parameter expansion to manipulate your strings.

while read -r line; do
  allbutlast1="${line%?}"          # strip the last character from $line
  lastchar="${line#$allbutlast1}"  # strip what we just captured from start of line
  allbutlast5="${line%?????}"      # strip the last 5 characters
  printf '%s%s\n' "$allbutlast5" "$lastchar"
done

Or if you're using bash as your shell, you have additional options:

while read -r line; do
  printf '%s%s\n' "${line:0:$(( ${#line} - 5))}" "${line:$(( ${#line} - 1 ))}"
done

(bash code compacted to save on throw-away variables.)

The POSIX code (first example) uses parameter expansions ${var%...} and ${var#...} to construct the output. The Bash code uses ${var:start:length} notation, with arithmetic expansion, $(( ... )).

This answer is included mostly for academic purposes. You'll get better performance using awk or sed than processing input line by line with a shell script.

Speaking of which, an awk solution might mirror the bash solution:

awk '{print substr($0,1,length($0)-5) substr($0,length($0))}'

Note that while bash's ${var:start:length} notation starts numbering characters at zero, awk's substr() function starts at one.

Upvotes: 0

Gambit Support
Gambit Support

Reputation: 1473

% cat input | sed 's/....\(.\)$/\1/'
abc2
e1kei95
e1edeaww6

Upvotes: 4

Related Questions