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 :

Récupération de texte entre crochets sous certaines conditions


Sujet :

Langage PHP

  1. #1
    Membre habitué
    Homme Profil pro
    Directeur technique
    Inscrit en
    Février 2011
    Messages
    146
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Directeur technique
    Secteur : Transports

    Informations forums :
    Inscription : Février 2011
    Messages : 146
    Points : 172
    Points
    172
    Par défaut Récupération de texte entre crochets sous certaines conditions
    Bonjour,

    Mon niveau en regex est un peu nooby donc je vous sollicite votre aide. Le but est de passer une (très grosse) application sous PHP4 vers PHP5, (oui ils ont laissé traîné la chose).

    en gros au lieu d'écrire : $VAR['ffff'] ils ont écrit : $VAR[ffff] (ffff n'étant évidement pas une constante)


    Le but est de faire un REGEX pour effectuer ce changement (plus de 450000 changements à opérer, en comptant certains que je ne dois évidement pas prendre)
    Tous est mélangé js / html etc...

    Le seul moyen est de détecter [VAR] qui est précédé par une variable php avec le $ (en gros détecter un tableau php)


    Voilà ou j'en suis :

    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
    $file = '
    sswhgs
    $hhh["wfwf"][dghj] => yes
    $hhh[\'cvcv\'][edtyu] => yes
    $hhh[dgddsf]["dtyudyt"] => yes
    xxdf["ert"][3dgdf5] 
    [sfg5] 
    $xxdf[dgdf5] => yes
    $hhh[fvsdf]["jft"][sfs] => yes (2times)
    ';
     
     
    preg_match_all('#\$[a-zA-Z_]{1}[a-zA-Z0-9_]*(.+)\[([a-zA-Z_]{1}[a-zA-Z0-9_]+)\]#U',
    $file,
    $out, PREG_PATTERN_ORDER);
     
    print_r($out);
    ce qui donne :
    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
    23
    24
    25
    26
    27
    28
    29
    30
    31
     
    Array
    (
        [0] => Array
            (
                [0] => $hhh["wfwf"][dghj]
                [1] => $hhh[\'cvcv\'][edtyu]
                [2] => $hhh[dgddsf]
                [3] => $xxdf[dgdf5]
                [4] => $hhh[fvsdf]
            )
     
        [1] => Array
            (
                [0] => hh["wfwf"]
                [1] => hh[\'cvcv\']
                [2] => hh
                [3] => xdf
                [4] => hh
            )
     
        [2] => Array
            (
                [0] => dghj
                [1] => edtyu
                [2] => dgddsf
                [3] => dgdf5
                [4] => fvsdf
            )
     
    )

    le but étant d'avoir en sortie :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
    sswhgs
    $hhh["wfwf"]['dghj'] => yes
    $hhh['cvcv']['edtyu'] => yes
    $hhh['dgddsf']["dtyudyt"] => yes
    xxdf["ert"][3dgdf5] 
    [sfg5] 
    $xxdf['dgdf5'] => yes
    $hhh['fvsdf']["jft"]['sfs'] => yes (2times)

    Je sais que je ne suis pas très loin mais il manque la solution quand il y en plusieurs encastrer les uns dans les autres ou à la suite.

  2. #2
    Expert éminent
    Avatar de Benjamin Delespierre
    Profil pro
    Développeur Web
    Inscrit en
    Février 2010
    Messages
    3 929
    Détails du profil
    Informations personnelles :
    Âge : 36
    Localisation : France, Alpes Maritimes (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Développeur Web
    Secteur : High Tech - Opérateur de télécommunications

    Informations forums :
    Inscription : Février 2010
    Messages : 3 929
    Points : 7 762
    Points
    7 762
    Par défaut
    Facile.

    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
    $buffer = <<< EOF
     
    \$a[foo] = 0;
    \$a[b]['c'] = 1;
    \$a["b"]['c'] = 2;
    \$a[] = 4;
     
    EOF;
     
    // capture les caractères alphanumériques
    // entre [ et ] (avec ou sans espace)
    $pattern = '~\[\s*([A-Za-z1-9]+)\*\]~';
     
    // et les mets dans une chaine
    // ($1 correspond à la première
    // parenthèse capturante de $pattern)
    $replace = '["$1"]';
     
    $buffer = preg_replace($pattern, $replace, $buffer);
     
    echo '<pre>'.$buffer.'</pre>';
    Pour voir comment utiliser les Regexp POSIX en PHP : http://php.net/manual/en/book.pcre.php

  3. #3
    Membre habitué
    Homme Profil pro
    Directeur technique
    Inscrit en
    Février 2011
    Messages
    146
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Directeur technique
    Secteur : Transports

    Informations forums :
    Inscription : Février 2011
    Messages : 146
    Points : 172
    Points
    172
    Par défaut
    hum, ton exemple ne semble pas marcher.

    Par ailleurs il faut garder à l'esprit qu'il ne faut pas modifier dans certains cas genre :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    echo '<input name="fff[STS]"' />';
    même chose avec le js, et d'autre bizarerie que j'ai pu voir.

    le $ doit être prit en compte.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    preg_match_all('#\$[a-zA-Z_]{1}[a-zA-Z0-9_]*(.+)\[([a-zA-Z_]{1}[a-zA-Z0-9_]*)\]#U',$buffer,$out, PREG_PATTERN_ORDER);
    le doit être remplacer par qq chose d'autre plus restrictif.

  4. #4
    Membre habitué
    Homme Profil pro
    Directeur technique
    Inscrit en
    Février 2011
    Messages
    146
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Directeur technique
    Secteur : Transports

    Informations forums :
    Inscription : Février 2011
    Messages : 146
    Points : 172
    Points
    172
    Par défaut
    par exemple ce cas là ne doit surtout pas être prit en compte :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    $DFHGFGH = "ffff[ffff]";

  5. #5
    Membre habitué
    Homme Profil pro
    Directeur technique
    Inscrit en
    Février 2011
    Messages
    146
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Directeur technique
    Secteur : Transports

    Informations forums :
    Inscription : Février 2011
    Messages : 146
    Points : 172
    Points
    172
    Par défaut
    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
    $file = <<< EOF
    \sswhgs
    \$h1["wfwf"][f1] => yes
    \$h2['cvcv'][f2] => yes
    \$h3[f3]["dtyudyt"] => yes
    xxdf["ert"][3dgdf5]
    xxdf["ert"][3dgdf5]
    [sfg5]
     
    \$DFHGFGH = "ffff[ffff]"; 
    \$kl=\$h4[f4] => yes
    \$h5[f5]["jft"][f6] => yes (2times)
    gdgd=[fg]\$ggg\$h6['fff']][f7] => yes 
    \$xhxfgh=\$h7[\$h8[f8]][f9]*\$xgfhxgh => yes (2times)
    EOF;
     
    preg_match_all('#\$[a-zA-Z_]{1}[a-zA-Z0-9_]*(\[([^\[]*)\])*\[([a-zA-Z_]{1}[a-zA-Z0-9_]*)\]#U',
    $file,
    $out, PREG_PATTERN_ORDER);
     
    print_r($out);
    le but est de récupérer les valeurs de f1 à f9.

    actuellement soit je récupère f8 ou f9 mais pas les 2 à la fois
    je récupère f5, mais en passant la moulinette un second coup je recupere f6.

    si qqn voit qq chose pour tout récupérer en un coup

  6. #6
    Membre habitué
    Homme Profil pro
    Directeur technique
    Inscrit en
    Février 2011
    Messages
    146
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Directeur technique
    Secteur : Transports

    Informations forums :
    Inscription : Février 2011
    Messages : 146
    Points : 172
    Points
    172
    Par défaut
    tjs pas d'idée lors de tableaux imbriqué les uns dans les autres ?

  7. #7
    Membre habitué
    Homme Profil pro
    Directeur technique
    Inscrit en
    Février 2011
    Messages
    146
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Directeur technique
    Secteur : Transports

    Informations forums :
    Inscription : Février 2011
    Messages : 146
    Points : 172
    Points
    172
    Par défaut
    après pas mal d'essaie :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    preg_match_all('/[^\\\\]\$[\w]+[\s]*[\-\>[\s]*[\w]+]?[\s]*(\[([\[[\s]*\'\w+\'[\s]*|[\s]*"\w+"[\s]*|[\s]*\$\w+\s]*\]])*\][\s]*)*[\s]*\[([\s]*[\w]+[\s]*)\]/U', $data, $out);

  8. #8
    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
    Bon en se basant sur ton expression suivante
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    preg_match_all('#\$[a-zA-Z_]{1}[a-zA-Z0-9_]*(.+)\[([a-zA-Z_]{1}[a-zA-Z0-9_]*)\]#U',$buffer,$out, PREG_PATTERN_ORDER);
    Pas la peine d'utiliser [...]{1} car une classe de caractère correspond déjà à UN seul caractère... Donc [...]{1} == [...]

    En cas de répitition, le parseur ne capture que la dernière occurence (ou la première selon le pattern), pour changer ce comportement, on peut utiliser \G qui signale au parseur de commencer la correspondance là où la dernière correspondance s'est terminée, ce qui permettra donc de capturer toutes les répétitions suivantes également... (pour plus d'infos sur \G, google est ton ami)

    Et donc, ton pattern devient:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    (?:\$[a-zA-Z_][a-zA-Z0-9_]*\[|\G(?<!^)).*?([a-zA-Z_][a-zA-Z0-9_]*)\]
    DEMO
    Une réponse utile vous a aidé ? N'oubliez pas le
    Votre problème est résolu ? N'oubliez pas le

  9. #9
    Membre habitué
    Homme Profil pro
    Directeur technique
    Inscrit en
    Février 2011
    Messages
    146
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Directeur technique
    Secteur : Transports

    Informations forums :
    Inscription : Février 2011
    Messages : 146
    Points : 172
    Points
    172
    Par défaut
    merci pour l'option G que je connaissais pas =)

    une petite amélioration avec
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    (\$[\w]+[\s]*(\-\>[\s]*[\w]+)?[\s]*([\s]*\[[\s]*("[\w]+"|\'[\w]+\'|\$[\w]+|[\w]+|\$[\w]+[\s]*(\-\>[\s]*[\w]+)?[\s]*([\s]*\[[\s]*("[\w]+"|\'[\w]+\'|\$[\w]+|[\w]+)[\s]*\][\s]*)*)[\s]*\][\s]*)*)[\s]*

Discussions similaires

  1. Réponses: 4
    Dernier message: 21/07/2010, 12h18
  2. Stopper une macro sous certaines conditions
    Par joquetino dans le forum VBA Access
    Réponses: 3
    Dernier message: 04/09/2008, 19h02
  3. Réponses: 9
    Dernier message: 28/08/2006, 09h58
  4. Réponses: 6
    Dernier message: 08/08/2006, 22h42

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