FAQ Langage JavaConsultez toutes les FAQ

Nombre d'auteurs : 41, nombre de questions : 296, dernière mise à jour : 8 mars 2017  Ajouter une question

 

Cette FAQ a été réalisée à partir des questions fréquemment posées sur le forum Java de http://java.developpez.com ainsi que l'expérience personnelle des auteurs.

Nous tenons à souligner que cette FAQ ne garantit en aucun cas que les informations qu'elle propose sont correctes. Les auteurs font leur maximum, mais l'erreur est humaine. Cette FAQ ne prétend pas non plus être complète. Si vous trouvez une erreur, ou que vous souhaitez nous aider en devenant rédacteur, lisez ceci.

Sur ce, nous vous souhaitons une bonne lecture.


SommaireBases du langageChaînes de caractèresExpressions régulières (3)
précédent sommaire suivant
 

Il est utile de « protéger » certaines chaînes de caractères avant de les utiliser dans une expression régulière. En effet, de nombreux caractères peuvent être interprétés par les regexp alors qu'on souhaite simplement représenter le caractère lui-même...

Le moyen le plus simple est de protéger ces caractères avec un antislash afin d'indiquer qu'ils ne doivent pas être interprétés... Toutefois, cette solution ne peut se limiter qu'à des expressions simples, et elle est complexe à mettre en place lorsque la chaîne provient d'une saisie utilisateur...

Dans ce cas, il est préférable d'utiliser les éléments de quotation \Q et \E. En effet, toute la sous-chaîne comprise entre ces deux éléments sera protégée lors de son traitement par les expressions régulières (il faut bien sûr penser à doubler l'antislash).

Il existe dans Java 5.0 une méthode statique permettant de protéger une chaîne simplement : Pattern.quote(String).
Pour information, cette méthode se contente généralement de renvoyer la chaîne entourée par \Q et \E. Elle gère toutefois le cas particulier où cette dernière contiendrait déjà le code \E.
Si vous n'utilisez pas encore Java 5.0, cette méthode correspond au code suivant :

Code java : Sélectionner tout
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
public static String quote(String s) { 
        int slashEIndex = s.indexOf("\\E"); 
        if (slashEIndex == -1) 
            return "\\Q" + s + "\\E"; 
  
        StringBuffer sb = new StringBuffer(s.length() * 2); 
        sb.append("\\Q"); 
        slashEIndex = 0; 
        int current = 0; 
        while ((slashEIndex = s.indexOf("\\E", current)) != -1) { 
            sb.append(s.substring(current, slashEIndex)); 
            current = slashEIndex + 2; 
            sb.append("\\E\\\\E\\Q"); 
        } 
        sb.append(s.substring(current, s.length())); 
        sb.append("\\E"); 
        return sb.toString(); 
    }

Mis à jour le 22 août 2015 adiGuba

Les expressions régulières permettent de créer des groupes lors d'un remplacement. Un groupe est simplement entouré de parenthèses. Ainsi, si on veut formater un texte HTML afin que toutes les occurrences d'une chaîne soient entourées par une balise <strong>, on peut utiliser le code suivant :

Code java : Sélectionner tout
1
2
String texte = "Un simple mot et un autre mot..."; 
String resultat = texte.replaceAll("(mot)", "<strong>$1</strong>");
Explication : Lors du remplacement, le contenu du groupe (mot) sera reporté dans la chaîne de remplacement par son indice ($1 en l'occurrence). Ainsi, dans notre exemple, le code $1 de la chaîne de remplacement sera remplacé par la chaîne "mot", pour obtenir :

Code html : Sélectionner tout
Un simple <strong>mot</strong> et un autre <strong>mot</strong>...
Ceci est d'autant plus utile lorsqu'on utilise un pattern plus complexe. Par exemple, pour créer des balises <a href/> lorsqu'on trouve une URL dans un texte, on peut utiliser le code suivant :

Code java : Sélectionner tout
1
2
String texte = "Bienvenue sur http://www.developpez.com !!!"; 
String resultat = texte.replaceAll("(http://[^ ]*)", "<a href='$1'>$1</a>");
Il est bien sûr possible d'utiliser plus d'un groupe, l'indice dépendra alors de la position du groupe dans le texte, sachant que la lecture se fait de gauche à droite. L'expression ((A)(B(C))) donnera :

  • $1 : ABC
  • $2 : A
  • $3 : BC
  • $4 : C

Il faut bien sûr veiller à ce que tous les groupes soient correctement fermés…

Mis à jour le 22 août 2015

Java, comme beaucoup d'autres langages, utilise le caractère antislash (« \ ») afin de représenter des caractères spéciaux, tels que \n et \t (pour le retour à la ligne et la tabulation), les quottes (\" et \') et les caractères Unicode (\u******** correspond au code Unicode).

Ceci afin de pouvoir les insérer dans une String ou un char, alors qu'ils ne sont pas forcément représentables dans un code source, ou qu'ils rentreraient en conflit avec la grammaire du langage...

Ainsi, lors de la compilation, ces séquences sont transformées vers leurs caractères équivalents. Donc, afin de pouvoir utiliser le caractère antislash comme un simple caractère, il faut utiliser la séquence le représentant, c'est-à-dire \\. D'ailleurs, si une séquence commençant par \ n'est pas reconnue par le compilateur, la compilation échouera (« invalid escape sequence »).

Ainsi, la chaîne "MOT1 \\ MOT2" dans le code source donnera bien MOT1 \ MOT2 lors de l'exécution du programme : pour représenter un caractère antislash, il faut le doubler.

Toutefois, bien qu'on ne souhaite représenter qu'un seul caractère \, il peut être parfois nécessaire de le quadrupler. En effet, le package java.util.regex permet de manipuler des Expressions régulières (ou regexp). Les expressions régulières représentent une famille de notations compactes et puissantes permettant de décrire des « modèles » (pattern) de chaînes de caractères. Elles utilisent pour cela un grand nombre de caractères spéciaux permettant de représenter d'autres ensembles de caractères (cf. la documentation de la classe Pattern pour plus de détails). Or il se trouve que les expressions régulières utilisent le caractère antislash afin de « protéger » ces caractères spéciaux, c'est-à-dire pour leur permettre d'être utilisés comme de simples caractères. Donc pour représenter le caractère antislash, il faut encore le doubler.
Étant donné que les expressions régulières interprètent la chaîne de caractères lors de l'exécution du programme, il faut donc qu'il soit quadruplé dans le code source (une fois à la compilation et une fois à l'exécution).

Exemples :

Code Source À l'exécution Interprétation des regexp
"abc\abc" Erreur de compilation : "invalid escape sequence : \a"  -
"abc\\abc" abc\abc abcabc (\a est équivalent à a pour les regexp)
"abc\\\abc" Erreur de compilation : "invalid escape sequence : \a"  -
"abc\\\\abc" abc\\abc abc\abc

Donc pour obtenir le caractère \ dans une expression régulière, il faut le quadrupler dans le code source !!!

Mis à jour le 22 août 2015 adiGuba

Proposer une nouvelle réponse sur la FAQ

Ce n'est pas l'endroit pour poser des questions, allez plutôt sur le forum de la rubrique pour ça


Réponse à la question

Liens sous la question
précédent sommaire suivant
 

Les sources présentées sur cette page sont libres de droits et vous pouvez les utiliser à votre convenance. Par contre, la page de présentation constitue une œuvre intellectuelle protégée par les droits d'auteur. Copyright © 2017 Developpez Developpez LLC. Tous droits réservés Developpez LLC. Aucune reproduction, même partielle, ne peut être faite de ce site et de l'ensemble de son contenu : textes, documents et images sans l'autorisation expresse de Developpez LLC. Sinon vous encourez selon la loi jusqu'à trois ans de prison et jusqu'à 300 000 € de dommages et intérêts.

 
Responsables bénévoles de la rubrique Java : Mickael Baron - Robin56 -