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

Langage PHP Discussion :

Une étoile capricieuse [RegEx]


Sujet :

Langage PHP

  1. #1
    Candidat au Club
    Homme Profil pro
    Développeur Web
    Inscrit en
    Avril 2014
    Messages
    3
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 35
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Avril 2014
    Messages : 3
    Points : 3
    Points
    3
    Par défaut Une étoile capricieuse
    Bonjour tous le monde,

    Je cherche un peu d'aide pour faire fonctionner ma regex, je ne comprend pas pourquoi l'étoile ou le + n'est pas efficace dans ma situation.

    Voici ma chaine : & § POULET # Robert § | & § MOUQUET # Jules § | 2eme § BERAUD # Henri § ! § | & § USTINOV # Peter §

    la regex que je n'arrive pas à faire fonctionner : (([^|]*)§([\w\s]+)#([\w\s]+)§([^|]*)([|]?))*

    le format que je respecte :
    [complement] § [nom co-auteur] # [prenom co-auteur] § [complement 2] | [complement] § [nom co-auteur2] # [prenom co-auteur2] § [complement 2] | [etc co-auteur suivant]

    si j'utilise cette regex, je n'ai comme résultat que mon dernier co-auteur, si j’enlève l'étoile et que je duplique ma regex ça fonctionne bien. Mais ça ne m'arrange pas car le nombre de co-auteur est indéfini.

    Je remercie d'avance toutes les personnes qui m'aideront !

    Loïc

  2. #2
    Membre habitué Avatar de denissay
    Homme Profil pro
    Inscrit en
    Mars 2006
    Messages
    103
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Belgique

    Informations forums :
    Inscription : Mars 2006
    Messages : 103
    Points : 125
    Points
    125
    Par défaut
    En effet, quand on utilise les quatificateurs, seule la dernière occurance est capturé...

    Si tu ne t'intérèsses qu'aux noms/prenoms, tu peux simplifier en:
    DEMO
    Une réponse utile vous a aidé ? N'oubliez pas le
    Votre problème est résolu ? N'oubliez pas le

  3. #3
    Candidat au Club
    Homme Profil pro
    Développeur Web
    Inscrit en
    Avril 2014
    Messages
    3
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 35
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Avril 2014
    Messages : 3
    Points : 3
    Points
    3
    Par défaut
    Merci grâce à toi je me suis rendu compte que je me compliqué un peu la vie.

    En effet, quand on utilise les quatificateurs, seule la dernière occurance est capturé...
    Je ne trouve pas ça très logique comme fonctionnement en tout cas !

    Au lieu d'utiliser l'étoile, le modifier "g" convient très bien à ce que je veux faire.

    Merci

  4. #4
    Expert éminent Avatar de CosmoKnacki
    Homme Profil pro
    Justicier interdimensionnel
    Inscrit en
    Mars 2009
    Messages
    2 858
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Charente Maritime (Poitou Charente)

    Informations professionnelles :
    Activité : Justicier interdimensionnel

    Informations forums :
    Inscription : Mars 2009
    Messages : 2 858
    Points : 6 556
    Points
    6 556
    Par défaut
    En réalité, toutes les occurrences sont capturées, mais quand on répète un groupe de capture, son contenu est remplacé à chaque nouvelle occurrence. C'est pour cela que tu te retrouves avec le dernier résultat.

    Concernant le modificateur g, bien que définit par PCRE (le moteur de regex utilisé par PHP), il n'existe pas directement en PHP. Le fait d'effectuer une recherche global ou pas dépend de la fonction qui est utilisée (preg_match recherche une seul correspondance (la première), preg_match_all les recherche toutes).

    Je te propose une méthode qui va extraire les champs, tout en vérifiant que la structure de la chaîne est conforme, pour éviter de fausses correspondances. (NB: cette vérification est peut être inutile ou disproportionnée dans ton cas, mais comme je n'en sais rien je le marque quand même.)


    Code php : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    <pre><?php
     
    $pattern = '~\G(?<comp>[^§]+) § (?<nom>[^#]+) # (?<prenom>[^§]+) §(?>[^§|]*§)?(?> \| |( *\z))~';
     
    $code = '& § POULET # Robert § | & § MOUQUET # Jules § | 2eme § BERAUD # Henri § ! § | & § USTINOV # Peter § ';
     
    if ( preg_match_all($pattern, $code, $matches, PREG_SET_ORDER) && isset(end($matches)[4]) ) {
        foreach ($matches as $match) {
            echo "\n{$match['comp']}\n{$match['nom']}\n{$match['prenom']}\n";
        }
    }

    \G est une ancre qui matérialise la position après la dernière occurrence, au début de la recherche, elle correspond au début de la chaîne.
    La syntaxe (?<toto>...) permet de donner un nom à ses captures.

    (?>[^§|])? c'est pour gérer le ! § bizarre à la fin du troisième enregistrement.

    (?> \| |( *\z)) est le point capital de la vérification. Soit on a | qui assure la jonction avec l'ancre \G du prochain enregistrement, soit on est en fin de chaîne. Dans ce cas, en plaçant cette alternative dans un groupe de capture (le groupe 4 donc), on peut vérifier que la chaîne est conforme du début à la fin en testant l'existence de ce groupe avec: isset(end($matches)[4]).
    Brachygobius xanthozonus
    Ctenobrycon Gymnocorymbus

  5. #5
    Candidat au Club
    Homme Profil pro
    Développeur Web
    Inscrit en
    Avril 2014
    Messages
    3
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 35
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Avril 2014
    Messages : 3
    Points : 3
    Points
    3
    Par défaut
    Merci pour cette réponse, en effet ça va m’être très utiles pour la suite !

    En réalité, toute les occurrences sont capturées, mais quand on répète un groupe de capture, son contenu est remplacé à chaque nouvelle occurrence. C'est pour cela que tu te retrouves avec le dernier résultat.
    Maintenant je comprend mieux le résultat !

    Concernant le modificateur g, bien que définit par PCRE (le moteur de regex utilisé par PHP), il n'existe pas directement en PHP
    Oui j'ai vu ça. ^^

    Je me coucherai moins bête ce soir ! thx !

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

Discussions similaires

  1. Réponses: 1
    Dernier message: 28/05/2007, 14h56
  2. une étoile filante ?
    Par pseudocode dans le forum Enigmes
    Réponses: 3
    Dernier message: 04/05/2007, 13h52
  3. Réalisation d'une étoile Filante
    Par bibendum7302 dans le forum Flash
    Réponses: 8
    Dernier message: 02/11/2006, 23h19
  4. Tracé d'une étoile à 5 branches
    Par onlytoine dans le forum 2D
    Réponses: 14
    Dernier message: 17/10/2005, 09h42
  5. Algorithme de tracé d'une étoile à 5 branches
    Par onlytoine dans le forum Algorithmes et structures de données
    Réponses: 6
    Dernier message: 14/10/2005, 17h50

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