I have file with many name: I want to replace only the first one
sed -i "s/\(name:\).*/\1 ${NEW_VALUE}/" ./myFile
Input
- martin:
name: Martin D'vloper
job: Developer
skills:
- python
- perl
- pascal
- tabitha:
name: Tabitha Bitumen
job: Developer
skills:
- lisp
- fortran
- erlang
output to change only the first name Martin D'vloper
- martin:
name: NEW VALUE!!!
job: Developer
skills:
- python
- perl
- pascal
- tabitha:
name: Tabitha Bitumen
job: Developer
skills:
- lisp
- fortran
- erlang
It changed all names
I saw something with different syntax
sed '0,/pattern/s/pattern/replacement/' filename
but I can't change sed to this because the dynamic value Could you advise me how to replace only the first one with my syntax ?
By default, the sed command replaces the first occurrence of the pattern in each line and it won't replace the second, third… occurrence in the line.
Find and replace text within a file using sed command Use Stream EDitor (sed) as follows: sed -i 's/old-text/new-text/g' input.txt. The s is the substitute command of sed for find and replace. It tells sed to find all occurrences of 'old-text' and replace with 'new-text' in a file named input.txt.
sed is a stream editor. A stream editor is used to perform basic text transformations on an input stream (a file or input from a pipeline). While in some ways similar to an editor which permits scripted edits (such as ed ), sed works by making only one pass over the input(s), and is consequently more efficient.
This should do what you want:
sed -i "0,/name:/{s/name:.*/name: ${NEW_VALUE}/}" ./myFile
It finds the first occurrence of name:
and then does the substitution, which is replace 'name: followed by any characters
' (.* means any sequence of characters) with 'name: ${NEW_VALUE}
' where NEW_VALUE
is your dynamical variable from your example.
From man sed
0,addr2
Start out in "matched first address" state, until addr2 is found. This is similar to 1,addr2, except that if addr2 matches the very first line of input the 0,addr2 form will be at the end of its range, whereas the 1,addr2 form will still be at the beginning of its range. This works only when addr2 is a regular expression.
If you are ok with awk
then please try following.
awk '/name/ && ++count==1{sub(/name:.*/,"name: NEW VALUE!!!")} 1' Input_file
In case you have a shell variable and you want to add its value to awk
code then try following.
val="new_vaue"
awk -v value="$val" '/name/ && ++count==1{sub(/name:.*/,"name: "value)} 1' Input_file
In case you want to save output into Input_file itself then append > temp_file && mv temp_file Input_file
to above code.
This might work for you (GNU sed):
sed -i "/\(name:\).*/{s//\1 ${NEW_VALUE}/;:a;n;ba}" ./myFile
Match on name:
, substitute new value and then read and print the remainder of the file.
Or alternative:
sed -z -i 's/\(name:\).*/\1 '"${NEW_VALUE}"'/M' file
N.B. the M
flag to the substitution command to restrict the .*
within a line.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With