Name: abc
Number: 325
Code: 0


Name: xyz
Number: 578
Code: 0


Name: ttt
Number: 356
Code: 0


Name: nnn
Number: 228
Code: 0


Name: bnb
Number: 434
Code: 0

Question is how to change Code to 1 but only if Number is 3xx or 2xx. So File2 and File5 remain unchanged.

Files have a lot more lines, and there are about 100 files, but this is just simplified example, how to replace one string in file (line x) but only if other string (line y) in that file is corresponding.

  • Could you, please, reformat your question ? So far, it suggests that all files contain only 1 line (but I guess this is not true), and this is actually pretty important to give you an answer that works. – Httqm May 24 '19 at 12:02
  • Does the Code: line always follow right after the Number: line? – steeldriver May 24 '19 at 13:18
  • @steeldriver No, Code: line isn't after the Number: line. – Siniša Babić May 24 '19 at 13:24

This should do the job :

sed -i 's/^Code: 0$/Code: 1/' $(grep -l '^Number: [23]' File*)
  • the sed part does the actual replacements
  • the grep -l ... File* part lists all files with name matching 'File*' and having a line starting with either Number: 2 or Number: 3
  • the $(...) construct surrounding the grep command is a command substitution that will feed files listed by grep into sed
| improve this answer | |
  • That assumes $IFS has not been modified and the file names don't contain space, tab newline or wildcard characters though. – Stéphane Chazelas May 24 '19 at 13:38

With GNU tools:

grep -lxZ 'Number: [23]..' ./File* |
  xargs -r0 sed -i 's/^Code: 0$/Code: 1/'
| improve this answer | |

Assuming Number always precedes Code, and Code might have any value, then using sed:

sed -i '/^Number: [23]/{n;s/^Code: .*$/Code 1/}' File*

If the content is consistent, so that the line after Number is always Code 0, that can be simplified to:

sed -i '/^Number: [23]/{n;s/0/1/}' File*
| improve this answer | |

Do not use sed for this task without creating temporary files because redirecting back to the source would destroy the file's contents. Instead, use the ed editor.
I assume that filenames are in the range [a-zA-Z0-9_-]

% cat scr.ed
1,$s/Code: 0/Code: 1/
% cat scr.sh
for file in `grep -l '^Number: [23]' File*`
    ed -s $file <scr.ed

% chmod 755 scr.sh
% ./scr.sh
| improve this answer | |
  • Is this a reply to another answer? – RalfFriedl May 24 '19 at 17:36
  • @RalfFriedl Did I write something impertinently? The question was "replace string in multiple files" and that's exactly what my solution is doing. Sed does not replace the string in the file but in the stream. – Slawomir Dziuba May 24 '19 at 17:46

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.