Regex palavra-break com diacríticos unicode
-
19-09-2019 - |
Pergunta
Eu estou trabalhando em um aplicativo que pesquisas de texto usando expressões regulares com base na entrada de um usuário. Uma opção que o usuário tem é a de incluir "um fósforo a 0 ou mais caracteres" wildcard usando o asterisco. Eu preciso disso para corresponder apenas entre os limites de palavra. Minha primeira tentativa foi para converter todos os asteriscos para (?:(?=\B).)*
, que funciona bem para a maioria dos casos. Onde ele falha é que, aparentemente, .Net considera a posição entre um caractere Unicode com um diacrítico e outro personagem uma palavra-break. Eu considero isso um erro, e apresentaram-lo para o Microsoft .
Enquanto isso, no entanto, eu preciso para obter a funcionalidade implementada e produto enviado. Estou pensando em usar [\p{L}\p{M}\p{N}\p{Pc}]*
como o texto de substituição, mas, francamente, estou em "Eu realmente não entendo o que isso vai fazer" terra. Quero dizer, eu posso ler as especificações, mas não estou confiante de que eu poderia suficientemente testar isso para ter certeza de que está fazendo o que eu espero. Eu simplesmente não sei todas as condições de contorno para teste. O aplicativo é usado por trabalhadores cross-culturais, muitos dos quais estão em locais tribais, portanto, quaisquer e todos os sistemas de escrita precisam ser suportados, incluindo alguns que usam quebras de palavras de largura zero.
Alguém tem uma solução mais elegante, ou poderia confirmar / corrigir o código acima, ou oferecer alguns ponteiros?
Obrigado por sua ajuda.
Solução
O equivalente a /(?:(?=\B).)*/
num contexto unicode seria:
/
(?:
(?: (?<=[\p{L}\p{M}\p{N}\p{Pc}]) (?=[\p{L}\p{M}\p{N}\p{Pc}])
| (?<![\p{L}\p{M}\p{N}\p{Pc}]) (?![\p{L}\p{M}\p{N}\p{Pc}])
)
.
)*
/
... ou um pouco simplificado:
/(?:[\p{L}\p{M}\p{N}\p{Pc}]+|[^\p{L}\p{M}\p{N}\p{Pc}]+)?/
Isto iria corresponder quer uma palavra ou de um não-palavra (espaçamento, pontuação, etc.) sequência, possivelmente um vazio.
A normal ou negada palavra-limite (\b
ou \B
) é basicamente um olhar em torno de casal. Um olhar para trás, certificando-se do tipo de personagem que precede a posição atual. Da mesma forma um olhar em frente.
Na segunda regex, eu removi os look-arounds e classes de personagens simples usado em seu lugar.