How to recursively replace strings (location path) in the files in directory, except binary files? I tried command

find . -type f -exec sed -i 's/foo/bar/g' {} +

but it replaces also strings in binary and other files(*.o, *.c). I want recursively replace strings in all files called ".depend".

  • 1
    .c files are usually C source files, not binary. – Kusalananda Jun 15 '19 at 22:15
  • It is all binary. Have you tried the -name or -iname option? – ctrl-alt-delor Jun 15 '19 at 22:40

find . -type f -name "*.depend" -exec sed -i 's/foo/bar/g' {} +


find . -type f -not -name "*.c" -not -name "*.o" -exec sed -i 's/foo/bar/g' {} +

       -name pattern
              Base of file name (the path with the leading directories
              removed) matches shell pattern pattern.  Because the leading
              directories are removed, the file names considered for a match
              with -name will never include a slash, so `-name a/b' will
              never match anything (you probably need to use -path instead).
              A warning is issued if you try to do this, unless the
              environment variable POSIXLY_CORRECT is set.  The
              metacharacters (`*', `?', and `[]') match a `.' at the start
              of the base name (this is a change in findutils-4.2.2; see
              section STANDARDS CONFORMANCE below).  To ignore a directory
              and the files under it, use -prune; see an example in the
              description of -path.  Braces are not recognised as being
              special, despite the fact that some shells including Bash
              imbue braces with a special meaning in shell patterns.  The
              filename matching is performed with the use of the fnmatch(3)
              library function.  Don't forget to enclose the pattern in
              quotes in order to protect it from expansion by the shell.


  • Well, how to exclude from search all binary files? A "binary" file is, according to grep, a file that contains character outside the printable ASCII range. Use grep -I option to distinguish between binary and non-binary files? – minto Jun 16 '19 at 14:41
  • 1
    This works for my purpose: find . -type f -exec grep -Iq . {} \; -exec sed -i 's|/foo|/bar|g' {} + – minto Jun 17 '19 at 11:29

I wrote this code, it works for my purpose:

find . -type f -exec grep -Iq . {} \; -exec sed -i 's|/foo|/bar|g' {} +

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.