IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

avec Java Discussion :

Pb de création de regex


Sujet :

avec Java

  1. #1
    Membre éprouvé
    Profil pro
    Inscrit en
    Septembre 2009
    Messages
    1 821
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2009
    Messages : 1 821
    Points : 979
    Points
    979
    Par défaut Pb de création de regex
    Bonjour,

    J'ai une chaine de caractère construite comment ceci:
    Une ligne contient 4 zones : chaque zone est séparée par une tabulation
    - la première zone doit contenir soit "IN" soit "OUT" soit "" (vide)
    - la seconde zone doit contenir soit "ERR" soit "" (vide)
    - la troisième zone doit contenir un mot (ne doit pas être vide ou ne doit pas contenir plusieurs mots)
    - la dernière zone doit contenir un ou plusieurs mot(ne doit pas être vide)

    Je pensais faire un tru du genre :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    "([IN][OUT][])\t([ERR][])\t(\\w+)\t([\\w+][\\w+ ]+)"
    => mais il ne fonctionne pas

    merci d'avance,

  2. #2
    Expert éminent sénior
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    Avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : Avril 2002
    Messages : 13 938
    Points : 23 190
    Points
    23 190
    Billets dans le blog
    1
    Par défaut
    Salut,


    C'est normal, ceci ([IN][OUT][]) signifie :
    • [IN] : une lettre parmi I ou N
    • [OUT] : une lettre parmi O, U ou T
    • [] : une lettre parmi aucune, soit rien


    Bref cela accepte les mots IO, IU, IT, NO, NU et NT...



    Ce que tu cherches à faire serait plus comme ceci : (IN|OUT|)



    Sinon perso je te conseillerais de bien éclater ton pattern et de bien le document. C'est déjà galère à lire donc autant rendre cela le plus clair possible :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    	String pattern = "(IN|OUT|)\t"	// "IN" "OUT" ou ""
    		+ "(ERR|)\t"		// "ERR ou ""
    		+ "(\\w+)\t"		// Un mot
    		+ "(\\w+[ \\w+]*)";	// Un mot, éventuellement suivi d'autre mots.

    a++

  3. #3
    Membre confirmé Avatar de Mobius
    Profil pro
    none
    Inscrit en
    Avril 2005
    Messages
    463
    Détails du profil
    Informations personnelles :
    Localisation : France, Isère (Rhône Alpes)

    Informations professionnelles :
    Activité : none

    Informations forums :
    Inscription : Avril 2005
    Messages : 463
    Points : 558
    Points
    558
    Par défaut
    dans une regexp "[IN]" indique que ton expression match avec "I" ou "N"

    Dans ton cas ta première zone match avec :
    - IO, IU, IT, NO, NU, NT

    Voici une expression (certainement pas parfaite mais) qui fonctionnerai :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    (IN)?(OUT)?\t(ERR)?\t(\S+)\t(.+)
    Le problème de ma regexp c'est qu'elle accepte une chaine commençant par "INOUT"

    Question: Pour ta 3° zone, un mot correspond a n'importe quelle suite de caractères alphanumérique (n'importe quelle caractère n'étant pas un espace, ou juste des caractère alphabétique) ?

    EDIT: Grillé (en plus avec une réponse de meilleur qualité)
    Librairie d'accès LDAP en Java : LdapBeans
    et pensez au tag

  4. #4
    Membre éprouvé
    Profil pro
    Inscrit en
    Septembre 2009
    Messages
    1 821
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2009
    Messages : 1 821
    Points : 979
    Points
    979
    Par défaut
    merci pour vos réponse mais je voudrais vraiment que mes test soient le plus strict possible.

    donc voici ma fonction de test :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    	void funcTestRegex(String str){
     
    		String pattern = "(IN|OUT|)\t"	// "IN" "OUT" ou ""
    			+ "(ERR|)\t"		// "ERR ou ""
    			+ "(\\w+)\t"		// Un mot
    			+ "(\\w+[ \\w+]*)";	// Un mot, éventuellement suivi d'autre mots.
     
     
    		Matcher matcher = Pattern.compile(pattern).matcher(str); 
     
    		if (matcher.find()){
    			// affichage des quatres zones
    			System.out.println("match ok :" + str);
    			System.out.println("\t group(1) :" + matcher.group(1).toString());
    			System.out.println("\t group(2) :" + matcher.group(2).toString());
    			System.out.println("\t group(3) :" + matcher.group(3).toString());
    			System.out.println("\t group(4) :" + matcher.group(4).toString());
     
    		} else {
    			System.err.println("match error :" + str);
    		}
    	}
    code testé :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    		funcTestRegex("IN\tERR\tsalut\tyo");
    		funcTestRegex("\tERR\tsalut\tyo");
    		funcTestRegex("ININ\tERR\tsalut\tyo");
    => les trois lignes passent le test alors que la dernière ne devrait pas

  5. #5
    Expert éminent sénior
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    Avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : Avril 2002
    Messages : 13 938
    Points : 23 190
    Points
    23 190
    Billets dans le blog
    1
    Par défaut
    Avec find() tu ne vérifies pas la totalité du format de la chaine, mais tu recherches une sous-chaine correspondant au pattern, et dans "ININ\tERR\tsalut\tyo" tu as la chaine ""IN\tERR\tsalut\tyo" qui correspond...

    Tu dois utiliser matches() qui vérifie que la chaine corresponde bien totalement au pattern :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    if (matcher.matches()) {
    a++

  6. #6
    Membre confirmé Avatar de Mobius
    Profil pro
    none
    Inscrit en
    Avril 2005
    Messages
    463
    Détails du profil
    Informations personnelles :
    Localisation : France, Isère (Rhône Alpes)

    Informations professionnelles :
    Activité : none

    Informations forums :
    Inscription : Avril 2005
    Messages : 463
    Points : 558
    Points
    558
    Par défaut
    tu peux utiliser "^" et "$" pour indiquer le début et la fin de chaine

    tu aura la regexp suivante : "^(IN|OUT|)\t(ERR|)\t(\\w+)\(\\w+[ \\w+]*)$"

    EDIT: Décidément j'ai trouvé plus rapide !! Par contre cette fois ci je ne sais pas quelle solution est la meilleur. (je soupçonne quand même que la méthode d'adiGuba soit meilleur)
    Librairie d'accès LDAP en Java : LdapBeans
    et pensez au tag

  7. #7
    Membre éprouvé
    Profil pro
    Inscrit en
    Septembre 2009
    Messages
    1 821
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2009
    Messages : 1 821
    Points : 979
    Points
    979
    Par défaut
    ok merci

    "^...$" => ça marche très bien.

    Il y a une différence de performance entre find et matches (sachant qu'en plus de tester le regex, il faut aussi que je récupère en même temps le contenu de mes zones)

    pour la dernière zone il faudrait aussi que je puisse puisse rajouter de la ponctuation (sauf sur le premier mot => il ne faut pas que la chaine commence par de la ponctuation), je pensais donc utiliser :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    		String pattern = "^(IN|OUT|)\t"	// le fichier commence par "IN" "OUT" ou ""
    			+ "(ERR|)\t"		// suivit de "ERR ou ""
    			+ "(\\w+)\t"		// suivit de Un mot
    			+ "(\\w+[ \\p\\w+]*)"	// suivit de Un mot, éventuellement suivi d'autre mots et de ponctuation.
    			+ "$";				// fin de la ligne
    => mais j'ai une erreur
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    Exception in thread "main" java.util.regex.PatternSyntaxException: Unknown character property name {\} near index 32
    ^(IN|OUT|)	(ERR|)	(\w+)	(\w+[ \p\w+]*)$
    ça vient de quoi ?

  8. #8
    Expert éminent sénior
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    Avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : Avril 2002
    Messages : 13 938
    Points : 23 190
    Points
    23 190
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par Mobius Voir le message
    Par contre cette fois ci je ne sais pas quelle solution est la meilleur. (je soupçonne quand même que la méthode d'adiGuba soit meilleur)
    D'un point de vue "technique" et "performance" je pense que c'est la même chose...

    D'un point de vue "sémantique" par contre il est préférable d'utiliser matches() qui indique qu'on souhaite vérifier que le format "corresponde" au pattern, et qui correspond apparemment exactement à l'objectif de boboss123.
    Alors que find() indique qu'on recherche le pattern dans une chaine.
    C'est de l'ordre du détail mais c'est plus clair :l a distinction existe dans l'API donc autant la faire nous aussi...


    Sinon d'après la Javadoc pour la ponctuation c'est \\p{Punct} et non pas \\p

    a++

  9. #9
    Membre confirmé Avatar de Mobius
    Profil pro
    none
    Inscrit en
    Avril 2005
    Messages
    463
    Détails du profil
    Informations personnelles :
    Localisation : France, Isère (Rhône Alpes)

    Informations professionnelles :
    Activité : none

    Informations forums :
    Inscription : Avril 2005
    Messages : 463
    Points : 558
    Points
    558
    Par défaut
    Citation Envoyé par adiGuba Voir le message
    D'un point de vue "technique" et "performance" je pense que c'est la même chose...
    L'implémentation est différente. En plus avec "^" et "$" l'expression régulière est plus longue donc certainement plus longue a compiler.

    Je ne vois pas pourquoi il y aurait deux implémentation autant différente s'il n'y avait pas de différence de performance.

    Je dis ça mais ce ne sont que des suppositions...
    Librairie d'accès LDAP en Java : LdapBeans
    et pensez au tag

  10. #10
    Membre éprouvé
    Profil pro
    Inscrit en
    Septembre 2009
    Messages
    1 821
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2009
    Messages : 1 821
    Points : 979
    Points
    979
    Par défaut
    merci beaucoup mon regex à l'air de bien fonctionner

    Citation Envoyé par adiGuba Voir le message
    Sinon d'après la Javadoc pour la ponctuation c'est \\p{Punct} et non pas \\p
    oups j'ai lu un peu trop rapidement la doc (pas lu jusqu'au bout lol)

    dernière petit question question, "[.^d]" ça veut dire quoi exactement ?
    => ce n'est pas la même chose que "[^d]" qui veut dire n'importe quel caractère sauf 'd'

  11. #11
    Expert éminent sénior
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    Avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : Avril 2002
    Messages : 13 938
    Points : 23 190
    Points
    23 190
    Billets dans le blog
    1
    Par défaut
    Je ne pense pas que ce soit si différent que cela. Le traitement doit être sensiblement le même si ce n'est que find() doit gérer un index de départ...

    Pour moi c'est la même chose qu'entre contains() ou indexOf() sur une chaine. Les deux permettent de savoir si une chaine contient une sous-chaine, mais la première est plus approprié pour cela


    a++

  12. #12
    Expert éminent sénior
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    Avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : Avril 2002
    Messages : 13 938
    Points : 23 190
    Points
    23 190
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par boboss123 Voir le message
    dernière petit question question, "[.^d]" ça veut dire quoi exactement ?
    => ce n'est pas la même chose que "[^d]" qui veut dire n'importe quel caractère sauf 'd'
    Cela veut dire : un caractère parmis ".", "^" ou "d".

    Le ^ n'a une signification particulière que lorsqu'il est en première position dans le [ ].
    Quand au point, il est n'a aucun sens spécial dans un bloc [ ]


    a++

  13. #13
    Membre éprouvé
    Profil pro
    Inscrit en
    Septembre 2009
    Messages
    1 821
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2009
    Messages : 1 821
    Points : 979
    Points
    979
    Par défaut
    oki, merci pour cet éclaircissement

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. [RegExp] Aide pour la création d'un regex
    Par beegees dans le forum Général JavaScript
    Réponses: 4
    Dernier message: 15/08/2011, 14h11
  2. création de regex
    Par heretik25 dans le forum Apache
    Réponses: 22
    Dernier message: 12/08/2011, 13h52
  3. Création d'une Regex (TextBox Float)
    Par snakzbenjy dans le forum Silverlight
    Réponses: 2
    Dernier message: 13/04/2011, 20h07
  4. [RegEx] Probleme de création d'un regex
    Par mathis49 dans le forum Langage
    Réponses: 6
    Dernier message: 15/06/2007, 12h08
  5. Regex : création de lien html s'il n'existe pas
    Par GregPeck dans le forum Langage
    Réponses: 3
    Dernier message: 22/11/2005, 00h21

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo