Unix 'find' + 'grep' syntax vs awk

I used this line to find the phrase “B206” in the files in the directory I was in and in all its subdirectories.

find . -exec grep -s "B206" '{}' \; -print 

Failure while trying to read certain files and actually changes the title bar in putty to a bunch of weird characters

For example, it is reset all the time when it gets to the jpg file, which is located in a subdirectory. The title bar changes and the screen has:

 ÐF»*rkNQeË+Z׳kU£~MÞçÄZ½ªéúýØâÑn¡[U+Þ4ªÒ9/ê£<ú¯4}[IÓîÃ¥K»G%ݳ¢ 

Forcing Ctrl + C back to the prompt and exit it.

Any way to add code to this line that will exclude jpg files? Even better, a piece of code, where can I add a list of extensions to exclude?


EDIT:
-not u-i don't work for me
I found this similar question , also related to my
+3
source share
12 answers

If your environment cannot do any fancy grep, then maybe your awk can do this:

 find . | awk '!/((\.jpeg)|(\.jpg)|(\.png))$/ {print $0;}' | xargs grep "B206" 
+3
source

There is no reason to use find : grep comes with the -r recursive option. To simply get a list of match file names (as opposed to a list of all matching lines in all files), you can use the -l option. If you want to completely ignore all binary files, you can use the --binary-files=without-match option. If you want to ignore files with a specific extension, you can use the --exclude , for example. --exclude=*.{jpg,jpeg} ignore all files ending in .jpg or .jpeg . So you should be able to get what you want:

 grep -r -l --binary-files=without-match . 

Now you mentioned in one of your comments that your version of grep does not have the -r or -l options. This is unfortunate, and I recommend getting a newer version of grep (preferably a variation of GNU).

One more note: if you use find -exec , you should use + to complete the command instead of a half ring, for example:

 find . -exec grep options '{}' '+' 

Using + , find will only throw away one process and pass all the corresponding file names as command line arguments to a single grep instance. As long as you don't have a million matching files (which would create a command line much longer than the shell can handle), it will be much faster. If a semicolon is used instead, find creates a new process for each corresponding file, which is very slow for a very large number of files.

+8
source

You can use the grep -I :

 Process a binary file as if it did not contain matching data; this is equivalent to the --binary-files=without-match option. 

In short, grep will simply assume that the file does not match, resulting in binary output.

+3
source

Just a quote, you do not need to close the terminal, you can use the reset command to restore the terminal output mode.

You can also run the previous grep to remove extensions you don't want:

 find -print | grep -v '\(\.jpg\|\.bmp\)$' | xargs grep "B206" 
+3
source
  find.  -type f -a -not -name \ *. jpg -exec grep -li "string" "{}" \;

This example uses Mac OSX 10.5, you will need to check the search page for your environment, as there is some discrepancy between GNU search and other vendor implementations. Solaris Validation (just for fun, the target OS was never specified):

  find.  -type f -a!  -name \ *. jpg -exec grep -li "string" "{}" \;

This construct finds all files whose names do not end with .jpg and execs grep for each of them.

Depending on your shell, you may need to avoid an explosion (!) To make it work as advertised.

+2
source

I tried the Erik command, but I got an error in the absence of the -grep predicate. My search version may be too old.

This worked for me:

 find . -type f -a -not -name \*.jpg -exec grep "B206" {} \; 
+2
source

Given the recent love affair over ack , I am surprised that no one has mentioned this yet.

You can customize types by extension so that you "grep" just the files you want. Or you can just use --nobinary, given the problem you are facing.

+2
source

If you have access to gfind, just add the expression "-not -name" * .jpg "to the expression.

 gfind . -not -name '*.jpg' -exec grep -s "B206" '{}' \; -print 

Another option (not necessary for this task, but a useful trick) is that if you want to use really fancy regular expressions, do

find some_easy_high_level_filter_expression -ls | perl -pe '{/ your_Perl_RegExp_of_choice /}'> ./files_to_search_in

grep options 'cat./files_to_search_in'

# the previous line should have backlinks, but I can’t make formatting avoid them

This sometimes gives the necessary advantage of caching a list of files in case you want to modify the grep expression to adjust it or just make more than 1 grep.

+1
source
 grep -r --exclude=*.jpg B206 . 

Sorry, with another comment:

Only GNU grep comes with -r (recursive), true UNIX grep does not. You must either install GNU grep or use it with find. - terminus

+1
source

To use grep with find, my syntax is:

 find . -name "*" -print | xargs grep B206 

All file filtering options, binary and everything, then the results are passed as arguments to the grep command.

+1
source

I think the problem is when you grep the binary, it outputs binary data. This binary data is somehow interpreted in your shell.

I would suggest trying to use the "strings" command, which ensures that your output will be text only, and then grep the output of the "strings".

+1
source

grep -I -r "string" *

0
source

Source: https://habr.com/ru/post/1286590/


All Articles