¿Grep distingue una variable y $ regex?
Quiero grep para una variable que tenga la cadena test, pero también quiero asegurarme de que solo encontrará testsi esa es la única palabra en una línea.
Entonces, probé esto:
string=test
echo "test" | grep "$string$"
Me gustaría saber si grepsabe que la primera parte, $string(en grep " $ string $"), pide buscar la cadena test, mientras que la última parte, $(en grep "$ string $ " pide buscar test, pero nada debe ir después testen la línea. ¿Es grepcapaz de distinguir $stringcomo una variable y solo $como la expresión regular para el final de la línea, o tengo que usar una cierta forma para distinguirlos?
Respuestas
Grep no sabe nada que no ve. Si grep ve $string$, intentará coincidir $string{end-of-line}. Lo que sucede es que el shell expande la variable $stringantes de que grepentre, de modo que greprecibe test$como regex.
Pero, dada la palabra $string$, ¿por qué el último $no se expande mientras que $stringes? Porque $no es un nombre de variable válido. Esto está muy claro en la especificación POSIX :
Si el parámetro no está entre llaves y es un nombre, la expansión debe usar el nombre válido más largo (ver Nombre XBD ), exista o no la variable representada por ese nombre.
Y el nombre XBD indica
En el lenguaje de comandos de shell, una palabra que consta únicamente de guiones bajos, dígitos y alfabéticos del conjunto de caracteres portátil. El primer carácter de un nombre no es un dígito.
Y también hay parámetros especiales , tales como $$, $@, $#, etc ..
Si no desea recordar todo esto, simplemente siga el consejo de Gordon Davisson y evite todo lo $que no debería introducir una variable para asegurarse de que se conservará.
$ echo "$string$" test$
$ echo "$string\$" test$
$ echo "\$string\$" $string$
También recuerde que las variables se expanden entre comillas dobles pero no entre comillas simples.
$ echo 'test' | grep '$string$' # No match, $string is not expanded $ echo 'test' | grep "$string$" # Match, $string is expanded
test
Quiero grep para una variable que tenga la cadena
test, pero también quiero asegurarme de que solo encontrarátestsi esa es la única palabra en una línea.
Para eso, necesita la expresión regular ^test$(para anclar la cadena tanto al inicio como al final de la línea) o usar la -xbandera degrep . Su intento original coincidiría Atestporque la expresión regular test$no está anclada al inicio de la línea.
$ echo Atest | grep "$string$"
Atest
$ echo Atest | grep -x "$string"
$ echo Atest | grep "^$string$"