apt-file regex: escapando de um ponto

3

Eu quero encontrar todos os pacotes que fornecem um objeto compartilhado contendo "ssl" no nome do arquivo. O man-arquivo do apt-arquivo diz:

  

- regexp | -x                 Trate o padrão como uma expressão regular (perl). Veja Perlreref (1)                 para detalhes. Sem essa opção, o padrão é tratado como um                 string literal para procurar.

Portanto, minha primeira tentativa foi

apt-file search --regexp .*ssl.*\.so.*

Isso, no entanto, me deu resultados como

  

espirituoso-exemplos: / usr / lib / Wt / examples / feature / client-ssl-auth / resources

que não tem ".so" no nome do arquivo.

Eu brinquei um pouco e inventei

apt-file search --regexp .*ssl.*\.so.*

i.e. Eu escapei da barra invertida que deveria escapar do ponto. Isso me deu os resultados que eu queria.

Alguém poderia explicar por que eu preciso de uma barra invertida dupla nesse caso?

    
por stackoverflowwww 04.07.2015 / 22:08

3 respostas

4

Você precisa de uma barra invertida dupla \ porque a barra invertida única não é apenas o caractere de escape regex, mas também o caractere usado pelo seu shell. Por exemplo. você escapa do ponto, que no nível de shell apenas interpreta em um ponto regular, que é então passado para o apt-get e macha todos os caracteres (como um ponto comum normalmente faz).

Então a resposta é, primeiro a string é interpretada pelo shell, onde a barra invertida tem um significado, e após , ela é passada para o apt-get. O mecanismo de regex do apt-get então interpreta a string pré-processada novamente. Lá, a barra invertida foi substituída (e também tem um significado ligeiramente diferente).

Outra solução é colocar o regex entre aspas, como em:

apt-file search --regexp '.*ssl.*\.so.*'
    
por con-f-use 04.07.2015 / 22:21
3

O problema é que, como você não está usando nenhuma citação, você precisa escapar tanto do interpretador shell quanto do interpretador de expressão regular para interpretar . como literal.

Essa é a razão pela qual a citação é importante. Seu primeiro padrão funcionaria se você apenas usasse aspas em torno dele:

apt-file search --regexp '.*ssl.*\.so.*'

A principal coisa a notar é que nosso objetivo final é deixar o intérprete regex de apt-file usar o . literalmente, e não da maneira usual, ou seja, qualquer caractere único.

O segundo caso:

apt-file search --regexp .*ssl.*\.so.*
  • O primeiro \ aqui é escapar do shell, pois o shell trata qualquer \ , já que a parte de backslash escapou de sequências, e. o shell trata \n como nova linha, \t como separador horizontal etc.

    Com um único \ como em .*ssl.*\.so.* , o shell trata . como \ caractere especial de escape, mas . não tem significado especial para shell, portanto, apenas \ é removido por shell deixando apenas um código%. Com . shell remove o primeiro \. deixando para trás \ como um literal \. é representado por \ no shell.

  • Portanto, temos \ deixado como o padrão Regex a ser interpretado pelo interpretador Perl Regex de .*ssl.*\.so.* . Então você obteria o resultado desejado.

por heemayl 04.07.2015 / 22:56
1

Se você não usa um padrão entre aspas, você tem que escapar da barra invertida para o RegEx:

apt-file search --regexp .*ssl.*\.so.*

Com um padrão entre aspas, você não precisa disso:

apt-file search --regexp '.*ssl.*\.so.*'

Exemplo

$ apt-file search --regexp .*ssl.*\.so.* > ~/tmp/bar
$ apt-file search --regexp '.*ssl.*\.so.*' > ~/tmp/foo
$ diff foo bar | wc -l
0
    
por A.B. 04.07.2015 / 22:22