¿Cómo puedo excluir una palabra con grep?


Respuestas:


802

Puede hacerlo usando la opción -v(for --invert-match) de grep como:

grep -v "unwanted_word" file | grep XXXXXXXX

grep -v "unwanted_word" filefiltrará las líneas que tienen unwanted_wordy grep XXXXXXXXsolo listará líneas con patrón XXXXXXXX.

EDITAR:

Según su comentario, parece que desea enumerar todas las líneas sin el unwanted_word. En ese caso, todo lo que necesitas es:

grep -v 'unwanted_word' file

2
¿Qué sucede si también quiero excluir N líneas después de la línea con "palabra no deseada"? -v 'unwanted_word' --after Nno ayuda porque INCLUYE la línea y N líneas después.
Andrey Regentov

-vo --invert-matchseleccione líneas no coincidentes. En tu caso grep -v 'unwanted_word' fileo grep --invert-match 'unwanted_word' file.
adamski.pro

Quiero ignorar una línea arriba y una línea abajo con un patrón coincidente. ¿Cómo puedo lograrlo?
Kanji Viroja

Impresionante, uso esto en git para examinar rápidamente el estado de mi repositorio, funciona como un encanto:git status -s |grep -v "folder_I_dont_care"
benjaminz

3
Extraño, es la respuesta principal, ¡pero en algunos casos está mal! Si quiero encontrar sun, excepto cuando es así sunrise, grep sun|grep -v sunrisesalta la línea que contiene ambos suny sunriseal mismo tiempo, eso no es lo que quiero. grep -P 'sun(?!rise)'es mucho mejor.
Greene

86

Entendí la pregunta como "¿Cómo hago coincidir una palabra pero excluyo otra?", Para lo cual una solución es dos greps en serie: primer grep encontrando la "palabra1" deseada, segundo grep excluyendo "word2":

grep "word1" | grep -v "word2"

En mi caso: necesito diferenciar entre "plot" y "#plot", que la opción "palabra" de grep no hará ("#" no es alfanumérico).

Espero que esto ayude.


16
Debe invertir el orden para resaltar word1.
Matthew leyó el

1
Supongo que aclararía agregar un marcador de posición para el nombre del archivo a ese ejemplo
patrick

39

Si grepadmite la expresión regular de Perl con la -Popción que puede hacer (si es bash; si es tcsh, deberá escapar de !):

grep -P '(?!.*unwanted_word)keyword' file

Manifestación:

$ cat file
foo1
foo2
foo3
foo4
bar
baz

Hagamos ahora una lista de todos fooexceptofoo3

$ grep -P '(?!.*foo3)foo' file
foo1
foo2
foo4
$ 

Gracias por esto, muy útil! Me gustaría mencionar que el comando grep
distingue entre

2
Tenga en cuenta que grep -v -Ptambién funciona sin negación en la expresión regular.
cybersoft

"si bash ... tendrás que escapar del !" . ¡Gracias, gracias, gracias! ¡Eso es lo que quería!
Gabriel Staples

36

La solución correcta es usar grep -v "word" file, con su awkequivalente:

awk '!/word/' file

Sin embargo, si tiene una situación más compleja en la que desea, por ejemplo, XXXaparecer y YYY no aparecer, entonces awkresulta útil en lugar de canalizar varios greps:

awk '/XXX/ && !/YYY/' file
#    ^^^^^    ^^^^^^
# I want it      |
#            I don't want it

Incluso puedes decir algo más complejo. Por ejemplo: quiero esas líneas que contienen XXXo YYY, pero no ZZZ:

awk '(/XXX/ || /YYY/) && !/ZZZ/' file

etc.


2
Parece ser mucho más rápido que la grep -Psolución en archivos grandes.
MBR

@MBR grep -Psignifica usar Perl regexp, por lo que cargar ese paquete será mucho más costoso de lo normal grep.
fedorqui 'SO deja de dañar'

10

Invierta la coincidencia utilizando grep -v:

grep -v "unwanted word" file pattern

6

grep proporciona la opción '-v' o '--invert-match' para seleccionar líneas no coincidentes.

p.ej

grep -v 'unwanted_pattern' file_name

Esto generará todas las líneas del archivo nombre_archivo, que no tiene 'patrón_no deseado'.

Si está buscando el patrón en varios archivos dentro de una carpeta, puede usar la opción de búsqueda recursiva de la siguiente manera

grep -r 'wanted_pattern' * | grep -v 'unwanted_pattern'

Aquí grep intentará enumerar todas las apariciones de 'wanted_pattern' en todos los archivos desde el directorio actual y pasarlo al segundo grep para filtrar el 'unwanted_pattern'. '|' - pipe le dirá a shell que conecte la salida estándar del programa izquierdo (grep -r 'wanted_pattern' *) a la entrada estándar del programa derecho (grep -v 'unwanted_pattern').


4

La -vopción le mostrará todas las líneas que no coinciden con el patrón.

grep -v ^unwanted_word

-5

Tengo un directorio con un montón de archivos. Quiero encontrar todos los archivos que NO contienen la cadena "speedup", así que utilicé con éxito el siguiente comando:

grep -iL speedup *

1
Desde la página de manual: "-L, --files-without-match Suprime la salida normal; en su lugar, imprima el nombre de cada archivo de entrada desde el que normalmente no se habría impreso ninguna salida. El escaneo se detendrá en la primera coincidencia " . por mí) ¡Así que ten cuidado con esto!
xuiqzy
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.