Diferença entre '.' , '?' e '*' em expressões regulares?

Diferença entre '.' , '?' e '*' em expressões regulares?

Posso obter um exemplo de como esses três elementos (são chamados de metacaracteres?) diferem?

Sei que isso *significa tudo ou nada, mas não tenho certeza se é a maneira certa de pensar sobre isso. Por outro lado .e ?parecem iguais. Eles combinam com um personagem, certo?

Responder1

Você pode estar confusoexpressões regularescomglobos de concha

Na sintaxe de expressão regular .representa qualquer caractere único (geralmente excluindo o caractere de nova linha), enquanto *é umquantificadorsignificando zero ou mais do átomo regex anterior (caractere ou grupo). ?é um quantificador que significa zero ouuminstâncias do átomo anterior ou (em variantes regex que o suportam) ummodificadorque define o comportamento do quantificador como não ganancioso.

Em shell globs, ?representa um único caractere (como o regex .) enquanto *representa uma sequência de zero ou mais caracteres (equivalente a regex .*).

Algumas referências que você pode achar úteis sãohttp://www.regular-expressions.info/quickstart.htmlehttp://mywiki.wooledge.org/glob

Responder2

Tirado direto deWikipédia:

? O ponto de interrogação indica zero ou uma ocorrência do elemento anterior. Por exemplo, color corresponde a "cor" e "cor".

*O asterisco indica zero ou mais ocorrências do elemento anterior. Por exemplo, ab*c corresponde a "ac", "abc", "abbc", "abbbc" e assim por diante.

A grande diferença é que o asterisco correspondezero ou maisocorrências, enquanto o ponto de interrogação correspondezero ou umocorrência. Compare estes dois exemplos:

$ printf "colour\ncolor\ncolouur\n" | egrep 'colou?r'                          
colour
color
$ printf "colour\ncolor\ncolouur\n" | egrep 'colou*r'                          
colour
color
colouur

Como na colouurletra u (o elemento anterior antes do qualificador ?) ocorreu mais de uma vez, não corresponde a ?, mas corresponde a*

Exemplo semelhante:

$ printf "error\neror\ner\n" | egrep 'er?or'                                   
eror
$ printf "error\neror\ner\n" | egrep 'er*or'                                   
error
eror

Da mesma página da Wikipedia:

Corresponde a qualquer caractere único (muitos aplicativos excluem novas linhas, e exatamente quais caracteres são considerados novas linhas são específicos do sabor, da codificação de caracteres e da plataforma, mas é seguro assumir que o caractere de alimentação de linha está incluído). Nas expressões de colchetes POSIX, o caractere de ponto corresponde a um ponto literal. Por exemplo, ac corresponde a "abc", etc., mas [ac] corresponde apenas a "a", "." ou "c".

Em nosso exemplo,

$ printf "colour\ncolor\ncolouur\n" | egrep 'colo.r'                           
colour
$ printf "colour\ncolor\ncolouur\n" | egrep 'colou.r'                          
colouur

Apropriadamente, o último é lido comomatch any line that has "colou", plus any character, plus letter "r"

Conclusão

Você perguntou: "Eu sei que '*' significa tudo ou nada, mas não tenho certeza se é a maneira correta de pensar sobre isso. Por outro lado, '.' & '?' parecem iguais." Como você pode ver, o ponto e o asterisco não são exatamente iguais. O ponto opera em qualquer caractere que possa estar ocupando aquela posição específica, enquanto o ponto de interrogação opera no elemento anterior.

Responder3

Nota: Examples provided are in Python.Embora o conceito permaneça o mesmo.

'.'é umsímbolo correspondenteque corresponde a qualquer caractere, excetocaractere de nova linha(isso também pode ser substituído por re.DOTALLargumentos em Python). Por isso também é chamado deCuringa.

'*'é umquantificador(define com que frequência um elemento pode ocorrer). É curto para{0,}.

Isso significa“corresponder a zero ou mais”—o grupo que precede a estrela pode ocorrer inúmeras vezes no texto. Pode estar completamente ausente ou repetido indefinidamente.

'?'também é umquantificador. É curto para{0,1}.

Isso significa"Corresponde a zero ou a um do grupo anterior a este ponto de interrogação."Também pode ser interpretado comoa parte que precede o ponto de interrogação é opcional.

por exemplo:

pattern = re.compile(r'(\d{2}-)?\d{10}')
mobile1 = pattern.search('My number is 91-9999988888')
mobile1.group()
Output: '91-9999988888'

mobile2 = pattern.search('My number is 9999988888')
mobile2.group()
Output: '9999988888'

No exemplo acima '?' indica que os dois dígitos que o precedem são opcionais. Podem não ocorrer ou ocorrer no máximo uma vez.

Diferença entre '.' e '?':

'.'corresponde/aceita/verificaqualquer caractere únicopara o lugar que ocupa na expressão regular.

por exemplo:

pattern = re.compile(r'.ot')
pattern.findall('dot will identify both hot and got.')
Output: ['dot', 'hot', 'got']

'?'corresponde/verifica a ocorrência zero ou única dogrupo que o precede.

Verifique o exemplo do número do celular.

O mesmo acontece com '*'. Ele irá verificarzero ou mais ocorrências do grupo que o precede.

Combinação:

'.*': Aceita quantas sequências estiverem disponíveis.Abordagem gananciosa.

'.*?'Aceita a primeira sequência correspondente e para.Abordagem não gananciosa

Para obter mais informações, considere ler as seguintes duas perguntas...

informação relacionada