Introdução
Não vejo muitos desafios de regex aqui, portanto, gostaria de oferecer esse enganosamente simples que pode ser feito de várias maneiras, usando vários sabores de regex. Espero que ele ofereça aos entusiastas de regex um pouco de diversão no golfe.
Desafio
O desafio é igualar o que denominei muito livremente de uma série "igualitária": uma série de números iguais de personagens diferentes. Isso é melhor descrito com exemplos.
Combine:
aaabbbccc
xyz
iillppddff
ggggggoooooollllllffffff
abc
banana
Não corresponde:
aabc
xxxyyzzz
iilllpppddff
ggggggoooooollllllfff
aaaaaabbbccc
aaabbbc
abbaa
aabbbc
Para generalizar, queremos corresponder a um assunto da forma ( para qualquer lista de caracteres para onde para todosc1)n(c2)n(c3)n...(ck)n
c1
ck
ci != ci+1
i, k > 1, and n > 0.
Esclarecimentos:
A entrada não estará vazia.
Um personagem pode se repetir mais tarde na sequência (por exemplo, "banana")
k > 1
, sempre haverá pelo menos 2 caracteres diferentes na string.Você pode assumir que apenas caracteres ASCII serão passados como entrada e nenhum caractere será um terminador de linha.
Regras
(Obrigado a Martin Ender por este bloco de regras excelentemente declarado)
Sua resposta deve consistir em um único regex, sem nenhum código adicional (exceto, opcionalmente, uma lista de modificadores de regex necessários para fazer sua solução funcionar). Você não deve usar recursos do tipo regex do seu idioma que permitam invocar código no idioma de hospedagem (por exemplo, o e
modificador do Perl ).
Você pode usar qualquer sabor de regex que existia antes deste desafio, mas especifique o sabor.
Não assuma que o regex esteja ancorado implicitamente, por exemplo, se você estiver usando Python, assuma que seu regex seja usado com re.search e não com re.match. Seu regex deve corresponder a toda a cadeia de caracteres para seqüências igualitárias válidas e não produzir correspondências para cadeias de caracteres inválidas. Você pode usar quantos grupos de captura desejar.
Você pode assumir que a entrada sempre será uma sequência de dois ou mais caracteres ASCII que não contém nenhum terminador de linha.
Como o regex golf, ganha o menor regex em bytes. Se o seu idioma exigir delimitadores (geralmente /.../
) para indicar expressões regulares, não conte os delimitadores. Se sua solução exigir modificadores, adicione um byte por modificador.
Critério
Este é um bom golfe à moda antiga, então esqueça a eficiência e tente obter o máximo de regex possível.
Mencione qual sabor de expressão regular você usou e, se possível, inclua um link mostrando uma demonstração online da sua expressão em ação.
fonte
banana
é igualitário.Respostas:
Sabor .NET, 48 bytes
Experimente online! (usando Retina )
Bem, acontece que não negar a lógica é mais simples, afinal. Estou fazendo disso uma resposta separada, porque as duas abordagens são completamente diferentes.
Explicação
fonte
((^.|\2(?=.*\4\3)|\4(?!\3))(?=\2*+((.)\3?)))+\3$
Eu estava experimentando\3*
no lugar de(?!\3)
fazê-lo 45b, mas isso falha em "aabbbc" :( A versão Perl é mais fácil de entender, e agora é 45b:^((?=(.)\2*(.))(?=(\2(?4)?\3)(?!\3))\2+)+\3+$
- a razão pela qual eu chamo Perl, mesmo que seja parece ser válido PCRE é que PCRE pensa(\2(?4)?\3)
poderia recurse indefinidamente enquanto Perl é um pouco mais esperto / perdoando!Sabor .NET, 54 bytes
Experimente online! (usando Retina )
Tenho certeza de que isso é subótimo, mas é o melhor que estou apresentando para equilibrar grupos no momento. Eu tenho uma alternativa na mesma contagem de bytes, que é basicamente a mesma:
Explicação
A idéia principal é inverter o problema, combinar cordas não igualitárias e colocar tudo em uma situação negativa para negar o resultado. O benefício é que não precisamos rastrear n em toda a cadeia (porque, devido à natureza dos grupos de balanceamento, você geralmente consome n ao verificá-la), para verificar se todas as execuções têm o mesmo comprimento. Em vez disso, procuramos apenas um único par de execuções adjacentes que não tenham o mesmo comprimento. Dessa forma, eu só preciso usar n uma vez.
Aqui está um detalhamento do regex.
fonte
banana
,aba
,bbbaaannnaaannnaaa
,bbbaaannnaaannnaaaaaa
,The Nineteenth Byte
,11
,110
,^(?!.*(?<=(\2)*(.))(?!\2)(?>(.)(?<-1>\3)*)(?(1)|\3)).+
,bababa
. Fui eu quem falhou. :( +1