Bash: sed substitution with an exclusion pattern

If you are doing a substitution with sed but need to exclude a specific line or pattern, that can be accomplished by prefixing an exclusion and using “!”.

For example, to substitute “hello” for “goodbye” in the following content, but to skip any line containing “world”, use syntax like the following:

$ sed "/world/! s/hello/goodbye/g" <<EOF
hello, world!
hello, galaxy!
hello, universe!
EOF 

hello, world!
goodbye, galaxy!
goodbye, universe!

This can be done with a more complex regex, but you do have to escape special characters  Here is an example of skipping lines containing “world” or “galaxy”.

$ sed "/\(world\|galaxy\)/! s/hello/goodbye/g" <<EOF
hello, world!
hello, galaxy!
hello, universe!
EOF

hello, world!
hello, galaxy!
goodbye, universe!

test_chain_sed.sh available on github.

REFERENCES

sed reference

stackoverflow, how to exclude specific patterns from substitution with sed

grymoire.com, sed examples of append, delete, range, etc