Quels caractères spéciaux doivent être échappés dans les expressions régulières?

Je suis fatigué de toujours essayer de deviner, si je devais échapper à des caractères spéciaux comme ‘ ()[]{}| ‘etc. lors de l’utilisation de nombreuses implémentations de regexps.

Il est différent avec, par exemple, Python, sed, grep, awk, Perl, rename, Apache, find, etc. Y a-t-il un ensemble de règles qui indique quand je devrais, et quand je ne devrais pas, échapper à des caractères spéciaux? Cela dépend-il du type regexp, comme PCRE, POSIX ou des expressions rationnelles étendues?

Les caractères que vous devez et que vous ne devez pas échapper dépendent de la saveur de regex avec laquelle vous travaillez.

Pour PCRE, et la plupart des autres versions compatibles avec Perl, échappez à ces classes de caractères externes:

 .^$*+?()[{\| 

et ces classes de caractères internes:

 ^-]\ 

Pour les expressions rationnelles POSIX étendues (ERE), échappez à ces classes de caractères externes (identiques à PCRE):

 .^$*+?()[{\| 

Echapper à d’autres caractères est une erreur avec POSIX ERE.

Dans les classes de caractères, la barre oblique inverse est un caractère littéral dans les expressions régulières POSIX. Vous ne pouvez pas l’utiliser pour échapper à quoi que ce soit. Vous devez utiliser “placement intelligent” si vous souhaitez inclure des métacaractères de classe de caractères en tant que littéraux. Mettez le ^ n’importe où, sauf au début, le] au début, et le – au début ou à la fin de la classe de caractères pour les faire correspondre littéralement, par exemple:

 []^-] 

Dans les expressions régulières de base POSIX (BRE), il s’agit de métacaractères que vous devez échapper pour supprimer leur signification:

 .^$* 

Echapper aux parenthèses et aux accolades dans BREs leur donne la signification particulière que leurs versions non échappées ont dans les ERE. Certaines implémentations (par exemple GNU) donnent également une signification particulière aux autres caractères lorsqu’ils sont échappés, tels que \? et +. Echapper à un caractère autre que. ^ $ * () {} Est normalement une erreur avec BRE.

Dans les classes de caractères, les règles BRE sont les mêmes que les règles ERE.

Si tout cela vous fait tourner la tête, prenez une copie de RegexBuddy . Sous l’onglet Créer, cliquez sur Insérer un jeton, puis sur Littéral. RegexBuddy va append des évasions si nécessaire.

Flavours RegEx modernes (PCRE)

Comprend C, C ++, Delphi, EditPad, Java, JavaScript, Perl, PHP (preg), PostgreSQL, PowerGREP, PowerShell, Python, REALbasic, Real Studio, Ruby, TCL, VB.Net, VBScript, wxWidgets, XML Schema, Xojo, XRegExp.
La compatibilité PCRE peut varier

Partout:. . ^ $ * + - ? ( ) [ ] { } \ |


Saveurs LegEx RegEx (BRE / ERE)

Comprend awk, ed, egrep, emacs, GNUlib, grep, PHP (ereg), MySQL, Oracle, R, sed.
Le support PCRE peut être activé dans des versions ultérieures ou en utilisant des extensions

ERE / awk / egrep / emacs

En dehors d’une classe de caractères:. . ^ $ * + ? ( ) [ { } \ |
Dans une classe de caractères: ^ - [ ]

BRE / ed / grep / sed

En dehors d’une classe de caractères:. . ^ $ * [ \
Dans une classe de caractères: ^ - [ ]
Pour les littéraux, n’échappez pas: + ? ( ) { } | + ? ( ) { } |
Pour un comportement regex standard, échappez: \+ \? \( \) \{ \} \| \+ \? \( \) \{ \} \|


Remarques

  • En cas de doute sur un caractère spécifique, il peut être échappé comme \xFF
  • Les caractères alphanumériques ne peuvent pas être échappés avec une barre oblique inverse
  • Les symboles arbitraires peuvent être échappés avec une barre oblique inverse dans PCRE, mais pas BRE / ERE (ils ne doivent être échappés qu’en cas de besoin). Pour PCRE ] - il suffit d’échapper à une classe de caractères, mais je les ai conservés dans une seule liste pour plus de simplicité
  • Les chaînes d’expression citées doivent également contenir les guillemets qui les entourent, et souvent avec des barres obliques inverses doublées (comme "(\")(/)(\\.)" /(")(\/)(\.)/ dans JavaScript)
  • Outre les échappements, différentes implémentations de regex peuvent prendre en charge différents modificateurs, classes de caractères, ancres, quantificateurs et autres fonctionnalités. Pour plus de détails, consultez le site regular-expressions.info , ou utilisez regex101.com pour tester vos expressions en direct

Malheureusement, il n’y a pas vraiment de jeu de codes d’échappement car il varie en fonction de la langue que vous utilisez.

Cependant, conserver une page comme la page des outils d’expression régulière ou cette astuce d’expression régulière peut vous aider à filtrer rapidement.

POSIX reconnaît plusieurs variations sur les expressions régulières – les expressions régulières de base (BRE) et les expressions régulières étendues (ERE). Et même alors, il y a des bizarreries à cause des implémentations historiques des utilitaires normalisés par POSIX.

Il n’y a pas de règle simple pour savoir quand utiliser quelle notation, ou même quelle notation utilise une commande donnée.

Découvrez le livre de Jeff Friedl intitulé Mastering Regular Expressions .

Malheureusement, la signification de choses comme (et \ (sont échangées entre les expressions régulières de style Emacs et la plupart des autres styles. Donc, si vous essayez d’échapper à ces expressions, vous faites peut-être le contraire de ce que vous voulez).

Donc, vous devez vraiment savoir quel style vous essayez de citer.

Parfois, une simple fuite n’est pas possible avec les caractères répertoriés. Par exemple, l’utilisation d’une barre oblique inverse pour échapper à un crochet ne fonctionnera pas dans la partie gauche d’une chaîne de substitution dans sed, à savoir:

 sed -e 's/foo\(bar/something_else/' 

J’ai plutôt tendance à utiliser une simple définition de classe de caractères, de sorte que l’expression ci-dessus devient

 sed -e 's/foo[(]bar/something_else/' 

que je trouve fonctionne pour la plupart des implémentations regexp.

BTW Les classes de caractères sont des composants d’expressions rationnelles plutôt vanille, donc ils ont tendance à fonctionner dans la plupart des situations où vous avez besoin de caractères échappés dans les expressions rationnelles.

Edit: Après le commentaire ci-dessous, j’ai pensé que je devrais mentionner le fait que vous devez également considérer la différence entre les automates à états finis et les automates à états non finis lorsque vous examinez le comportement de l’évaluation regexp.

Vous voudrez peut-être regarder “le livre de balle shiny” aka Effective Perl ( lien Amazon assaini ), en particulier le chapitre sur les expressions régulières, pour avoir une idée de la différence dans les types d’évaluation du moteur d’expression régulière.

Pas tout le monde un PCRE!

Quoi qu’il en soit, les regexp sont tellement maladroites que SNOBOL ! C’était un cours de programmation intéressant! Avec celui de Simula .

Ah les joies d’étudier à l’UNSW à la fin des années 70! (-:

Vraiment, il n’y en a pas. il y a environ une demi-zillion de syntaxes différentes de regex; ils semblent se résumer à Perl, EMACS / GNU et AT & T en général, mais je suis toujours aussi surpris.

Pour PHP, “il est toujours prudent de faire précéder un caractère non alphanumérique de” \ “pour spécifier qu’il se représente lui-même.” – http://php.net/manual/en/regexp.reference.escape.php .

Sauf si c’est un “ou”.: /

Pour échapper aux variables du modèle de regex (ou aux variables partielles) en PHP, utilisez preg_quote ()