Reputation: 103
I need to swap only numeric values in each line after specific string "PIC" using sed. For example:
hello PIC A(12), and this PIC B(11)
The desired output is :
hello PIC B(11), and this PIC A(12)
The characters "B" and "A" might differ in other lines, but the string PIC is always there.
I am trying to use sed command :
echo "hello PIC A(12), and this PIC B(11)" | sed '/PIC X(12)/s/PIC X(12)/PIC X(11)/g'
but seems not working properly.
All responses are appreciated.
Upvotes: 2
Views: 111
Reputation: 204015
With any POSIX sed:
$ sed 's/\(PIC [[:upper:]]([0-9]*)\)\(.*\)\(PIC [[:upper:]]([0-9]*)\)/\3\2\1/' file
hello PIC B(11), and this PIC A(12)
If you don't have a POSIX sed (e.g. old sed on Solaris) then set LC_ALL=C
and change [:upper:]
to [A-Z]
.
Upvotes: 1
Reputation:
if data in 'd' file, tried on gnu sed
sed -E 's/(hello PIC )(\w+)(\S+, and this PIC )(\w+)/\1\4\3\2/' d
Upvotes: 1
Reputation: 627103
You may use the substitute
command directly since it will only change the lines where the match is found.
Use this POSIX ERE
sed -E 's/(PIC )([A-Z]\([0-9]+\))(.*PIC )([A-Z]\([0-9]+\))/\1\4\3\2/'
Or, POSIX BRE
sed 's/\(PIC \)\([A-Z]([0-9]*)\)\(.*PIC \)\([A-Z]([0-9]*)\)/\1\4\3\2/'
The two versions differ in the parentheses escaping: in POSIX BRE, \(...\)
denote capturing groups and (
and )
are matching literal parentheses, while in POSIX ERE, it is vice versa.
POSIX ERE pattern details:
(PIC )
- Group 1: PIC
and space([A-Z]\([0-9]+\))
- Group 2: any uppercase ASCII letter, (
, 1+ digits, )
(.*PIC )
- Group 3: any 0 or more chars, PIC
, space([A-Z]\([0-9]+\))
- Group 4: an uppercase letter, (
, 1+ digits, )
.Upvotes: 2