Chaitan Yadav
Chaitan Yadav

Reputation: 115

Replace 1st Occurence line with Value1 and 2nd Occurence line with Value2 using sed

I'm stuck with requirement where I have to replace first occurrence keyword{as well as whole line} with value x and 2nd occurrence with value Y. For example

  1. sudo docker push IP:PORT/ABC:1

  2. sudo docker push IP:PORT/XYZ:1

In above case, I would select using keyword "sudo docker push" and replace 1st occurrence whole line with sudo docker push IP1:PORT/ABC:1 and 2nd occurrence whole line with sudo docker push IP2:PORT/ABC:1.

I have tried following combinations but nothing has worked until now :

sed -i "s,old-word,new-word," file-name
sed -i "<occurence-number> s,old-word,new-word,g" file-name
sed -i " s,old-word,new-word,<occurence-number>g" file-name
sed "<occurence-number>,old-word,{s,old-word,new-word,}" file-name

Upvotes: 0

Views: 83

Answers (4)

Pierre Fran&#231;ois
Pierre Fran&#231;ois

Reputation: 6073

If you allow me to rephrase your question:

The file named file-name containing v.gr.

some lines
...
sudo docker push IP:PORT/ABC:1
more lines
...
sudo docker push IP:PORT/ABC:1
and so on
...

must be changed into:

some lines
...
sudo docker push IP1:PORT/ABC:1
more lines
...
sudo docker push IP2:PORT/ABC:1
and so on
...

The difficulty is that two occurences of the same key must trigger two different changes.

Try this script:

#!/bin/bash

key="sudo docker push"
#Caution: "/" inside the two strings below must be escaped as "\/"
change1="sudo docker push IP1:PORT\/ABC:1"
change2="sudo docker push IP2:PORT\/ABC:1"

sed -i "
  0,/$key/s/^.*$key.*$/FIRST-OCCURENCE/
  0,/$key/s/^.*$key.*$/$change2/
  /FIRST-OCCURENCE/s//$change1/
" file-name

Upvotes: 1

McLeon
McLeon

Reputation: 66

Try this

sed -i "/old-word/c new-word" file-name

Upvotes: 0

Socowi
Socowi

Reputation: 27285

It is possible with sed, but very inconvenient:

sed '/OLD/{s|.*|NEW-1|; :label; n; /OLD/s|.*|NEW-2|; b label;}'

Depending on your version of sed, you might have to replace the ; after :label and b label with a literal linebreak to make this work.

For the input …

a b c
d OLD e
f g h
i OLD k
l m n

… this prints …

a b c
NEW-1
f g h
NEW-2
l m n

For simplicity, you might want to use awk instead:

awk '/OLD/ {++c; if (c==1) {$0="NEW-1"} else {$0="NEW-2"}} 1'

or

awk 'BEGIN {a[1]="NEW-1"; a[2]="NEW-2"} /OLD/ {$0=a[++c]} 1'

Upvotes: 0

Saboteur
Saboteur

Reputation: 1428

Example is not clear... it will be better to provide full string example of what you have and what you want in the result. But maybe you are looking for "sudo docker push" and trying to replace only this part, instead of whole line. You can use regexp to select rest of line, like that:

sed -i 's/sudo docker push.*/sudo docker push IP:PORT/XYZ:1/'

Or just provide more clear example of origin and result strings.

Upvotes: 0

Related Questions