Observo el siguiente comportamiento de grep
al ejecutarlo cinco veces:
me@asus:~/go/src/company/topology-front$ lsof |grep "READ" vim 4788 me 4u REG 8,2 12288 32247694 /home/me/go/src/company/topology-front/.README.md.swp me@asus:~/go/src/company/topology-front$ lsof |grep "README.md*" vim 4788 me 4u REG 8,2 12288 32247694 /home/me/go/src/company/topology-front/.README.md.swp me@asus:~/go/src/company/topology-front$ lsof |grep "README.md" vim 4788 me 4u REG 8,2 12288 32247694 /home/me/go/src/company/topology-front/.README.md.swp me@asus:~/go/src/company/topology-front$ lsof |grep "*README.md*" me@asus:~/go/src/company/topology-front$ lsof |grep "*README.md" me@asus:~/go/src/company/topology-front$
No pude «entender por qué los dos últimos intentos de grep
no devuelven ningún resultado .
Respuesta
grep
Los patrones son expresiones regulares (también conocidas como regex, regexp, RE), expresiones regulares básicas (BRE) a menos que una de -E
/ -F
/ / -K
/ -X
(solo las dos primeras son estándar).
*
es un operador de expresión regular que coincide con 0 o más del átomo anterior. Por ejemplo, d*
coincide con 0 o más d
s. En BRE, cuando se encuentra al comienzo del patrón o cuando se sigue el
o \(
operadores regexp, coincide con un *
literal solamente (también se literalmente dentro de [...]
expresiones entre corchetes).
Entonces grep "*README.md*"
coincide con las líneas que contienen un seguido de README
seguido de cualquier carácter (el .
operador regexp) seguido de m
seguido de cualquier número de d
s. Dado que cualquier número incluye 0, eso «es funcionalmente equivalente a grep "*README.m"
(lo que no haría ninguna diferencia con las líneas que coinciden, solo en las que pueden coincidir dentro de la línea (que se mostraría con la opción --color
de GNU grep
por ejemplo)).
Por ejemplo , coincidiría en esas 2 líneas:
*README mike ^^^^^^^^^ DONT***README-mddd ^^^^^^^^^^^^
(las ^
s que muestran lo que dentro de la línea coincide por la expresión regular, que podría ver con --color
)
Aquí, parece que está confundiendo expresiones regulares con patrones de comodines de shell. El *
operador comodín que coincide con 0 o más caracteres se puede escribir .*
en expresiones regulares. Pero hacer:
grep ".*README\.md.*"
volvería a ser lo mismo que:
grep "README\.md"
Como grep
busca una coincidencia dentro de la línea en lugar de buscar líneas que coincidan exactamente con el patrón (para lo cual necesitas -x
).
Con ast-open grep
, que también es ksh93
«s grep
incorporado (no siempre está incorporado de forma predeterminada, y debe habilitarlo poniendo /opt/ast/bin
antes de $PATH
), puede usar la opción -K
para grep
para usar comodines de shell (ksh93 extendidos). Entonces, con eso grep
implementación, puede hacer:
grep -K "README.md"
o
grep -xK "*README.md*"
para hacer coincidir las líneas que contienen README.md
.
Con esa misma implementación, la coincidencia de comodines también se puede habilitar dentro de extendido (), aumentado (-X
) o tipo perl (-P
) regular expresiones con el operador (?K)
(y \(?K\)
en expresiones regulares básicas que realmente rompen la conformidad con POSIX, por lo que no confiaría en él ya que podría eliminarse en una versión futura). Entonces puede hacer:
grep -xE "(?K)*README.md*"
allí.
Con cualquier implementación moderna de grep
, también puede hacer:
grep -F README.md
Para una búsqueda de cadena fija (donde .
arriba coincide con un .
en lugar de cualquier carácter).
*
o+
al comienzo de la expresión regular, y tambiéngrep -P
grep -E
con varias implementaciones. Eso*
se trata literalmente cuando al principio solo se especifica para BRE. Con otros RE, YMMV.grep
simple (ogrep -G
).grep -K
que usa patrones de shell (donde*
coincide con cualquier número de caracteres).*
no es especial cuando aparece el primer carácter de un BRE, consulte la especificación POSIX