2017-10-21 111 views
0

J'ai essayé de chercher beaucoup pour cela, et il y a des problèmes similaires mais je n'ai pas réussi à comprendre cela.Regex, tout entre deux caractères sauf les caractères d'échappement

Mon problème est que j'ai, entre autres, des chaînes sur cette forme:

%Aliquam hendrerit mollis pretium! Praesent id% 
%molestie \*libero vel\%\% pulvinar? Sed% 
\%% urna. \% Fusce% in *sapien %mau\*ris.% 

Je veux tout sélectionner entre deux% s, sans tenir compte des cas où les personnages sont précédés par un \. Le premier est trivial, et j'ai réussi à faire le second. Le troisième cependant je ne peux pas comprendre. Pour clarifier, du texte ci-dessus, je veux sélectionner les éléments suivants:

"!% Aliquam hendrerit id mollis pretium Praesent%"

"% molestie * libero vel \% \% pulvinar Sed%?"

"% Urna. \% Fusce%"

"% mau * Ris.%"

voulez-vous signaler que le texte original peut être une partie d'une longue chaîne sans saut de ligne, à savoir chaque ligne n'apparaît pas nécessairement sur nouvelles lignes.

jusqu'ici j'ai écrit l'expression régulière suivante qui semble être en mesure de faire correspondre tout sauf le dernier:

(?<!\\)%([^%]*)(?!%\\)(?:%|(.*)%)(?<!\\%) 

Pour la dernière, il sélectionne:.

« % Urna \% Fusce% in * sapien% mau * ris.% "

Ce qui est trop. Je ne comprends pas vraiment pourquoi il le fait, c'est peut-être à cause de la condition-or dans mon regex? Toute aide est très appréciée!

+0

Ne pouvez-vous pas supprimer les caractères d'échappement dans un deuxième temps? 's /\\.// g'. Et je suis un peu confus, voulez-vous que tous les chars échappés soient ignorés, ou seulement ignorés? Votre question indique un résultat attendu différent de celui fourni par votre exemple. – knittl

+0

Le problème est que les caractères échappés sont autorisés, donc je ne peux pas les enlever. Et j'éditerai le post principal pour éclaircir la confusion, désolé pour ça! EDIT: J'ai édité le post principal avec des exemples corrects de ce que je veux être en mesure de sélectionner. – Scheme

Répondre

0

Ce regex vous donnera le résultat escompté:

/(?<!\\)(%.*?(?<!\\)%)/ 

Voir cette Regex101.com

Explication

1 - (?<!\\)% correspond à tout caractère% non précédé d'une barre oblique inverse.

2-.*? correspond à tout caractère d'une manière paresseuse

3 - Environnement (2) avec (1) correspond à tout caractère entourée d'un% n'a pas été précédée par une barre oblique inverse.

+0

En effet, merci beaucoup! – Scheme

+0

De rien. Ajout d'explications pour vous aider à comprendre le processus. –