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 Perl Discussion :

Trouver les bonnes accolades fermantes !


Sujet :

Langage Perl

  1. #1
    Nouveau Candidat au Club
    Profil pro
    Inscrit en
    Décembre 2006
    Messages
    5
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Décembre 2006
    Messages : 5
    Points : 1
    Points
    1
    Par défaut Trouver les bonnes accolades fermantes !
    Bonjour à tous

    Dans une chaîne je cherche à extraire tout ce qui est compris entre {{ et }}
    -> $entry =~ s/\{\{([^\}]*)\}\}/&EntryReplaceMsgTag($1)/ge ;

    Mais voila si ma chaîne contient d'autres accolades ce n'est plus bon !
    exemple : {{ toto {{tata}} }}, dans ce cas je veux récuperer toto {{tata}}
    Comment faire ?

    Pour résumer comment trouver la bonne accolade fermante d'une ouvrante ?

    Merci pour votre aide !

  2. #2
    Membre éprouvé Avatar de MarneusCalgarXP
    Profil pro
    Inscrit en
    Juillet 2006
    Messages
    911
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France, Nord (Nord Pas de Calais)

    Informations forums :
    Inscription : Juillet 2006
    Messages : 911
    Points : 1 118
    Points
    1 118
    Par défaut
    Dans ce cas, il faut jouer avec le début de la ligne (^) et la fin de la ligne ($), en précisant que tu cherches tout ce qui se trouve entre les 1° accolades ouvrantes et les dernières accolades fermantes, et dire dans ton bloc capturant que tu veux n'importe quel caractère:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    $entry =~ s/\^.*?\{\{(.*)\}\}.*?$/&EntryReplaceMsgTag($1)/ge ;

    Je ne répond à aucune question technique par MP.

    Si votre problème est réglé, n'oubliez pas Dans tous les cas

  3. #3
    Nouveau Candidat au Club
    Profil pro
    Inscrit en
    Décembre 2006
    Messages
    5
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Décembre 2006
    Messages : 5
    Points : 1
    Points
    1
    Par défaut
    Citation Envoyé par MarneusCalgarXP
    Dans ce cas, il faut jouer avec le début de la ligne (^) et la fin de la ligne ($)
    Merci pour la réponse, mais j'ai oublié de préciser que mon texte est sur plusieurs lignes...

    le {{toto est {{l'ami}}
    des animaux}} et des plantes

    et je dois avoir :

    toto est {{l'ami}}
    des animaux

    et non pas
    toto est {{l'ami

    Dur Dur!

  4. #4
    Rédacteur/Modérateur

    Avatar de Antoun
    Homme Profil pro
    Architecte décisionnel
    Inscrit en
    Octobre 2006
    Messages
    6 280
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 53
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Architecte décisionnel
    Secteur : Conseil

    Informations forums :
    Inscription : Octobre 2006
    Messages : 6 280
    Points : 11 736
    Points
    11 736
    Par défaut
    tu te limites à un seul niveau d'imbrication, ou il peut y en avoir un nombre arbitraire ? (du genre {{abd {{ def {{ ghi}} jkl }} mno }}pqr)
    Antoun
    Expert Essbase, BO, SQL

    La bible d'Essbase, 2ème édition

  5. #5
    Rédacteur/Modérateur

    Avatar de Antoun
    Homme Profil pro
    Architecte décisionnel
    Inscrit en
    Octobre 2006
    Messages
    6 280
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 53
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Architecte décisionnel
    Secteur : Conseil

    Informations forums :
    Inscription : Octobre 2006
    Messages : 6 280
    Points : 11 736
    Points
    11 736
    Par défaut
    ça y est, je l'ai ! quel que soit le niveau d'imbrication :

    $entry =~ s/\^.*?\{\{([^{]*)\}\}.*?$/&EntryReplaceMsgTag($1)/ges ;

    si tu veux autoriser un { isolé à l'intérieur des {{...}}, c'est ([^{]|\{[^{])*
    Antoun
    Expert Essbase, BO, SQL

    La bible d'Essbase, 2ème édition

  6. #6
    Membre confirmé
    Profil pro
    Inscrit en
    Juin 2006
    Messages
    427
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2006
    Messages : 427
    Points : 459
    Points
    459
    Par défaut
    cpan à la rescousse: Text::Balanced
    http://search.cpan.org/~dconway/Text...xt/Balanced.pm
    Recherche staigiaire(s) motivé(s) sur projet perl/reseau a grande echelle. Me contacter par mp.

  7. #7
    Nouveau Candidat au Club
    Profil pro
    Inscrit en
    Décembre 2006
    Messages
    5
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Décembre 2006
    Messages : 5
    Points : 1
    Points
    1
    Par défaut
    Merci à tous,
    Je n'y arrive pas !

    j'ai par exemple :
    c'est {{{{la}} faute {{à}}}} {{la}} voisine {{et voila}}.
    et le résultat doit être
    {{la}} faute {{à}}

    c'est à dire que dés que j'ai {{, je dois extraire la chaîne jusqu'au bon
    }} fermant, sans tenir compte des éventuels {{ }} inclus !

    Je ne peux pas me baser sur la fin de ligne !
    Et je n'ai pas l'impression que &extract_bracketed fonctionne bien avec des
    délimiteurs doubles

    Je tourne en rond

  8. #8
    Rédacteur/Modérateur

    Avatar de Antoun
    Homme Profil pro
    Architecte décisionnel
    Inscrit en
    Octobre 2006
    Messages
    6 280
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 53
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Architecte décisionnel
    Secteur : Conseil

    Informations forums :
    Inscription : Octobre 2006
    Messages : 6 280
    Points : 11 736
    Points
    11 736
    Par défaut
    tu as essayé la mienne (avec le /s et en slurp mode) ?

    je n'ai pas eu le temps de la tester (il peut donc rester des pétouilles), mais je suis sûr du principe, càd utiliser [^{] au lieu de . dans les parenthèses capturantes.

    si tu n'y arrive pas dans la journée, j'essaie de te faire ça ce soir.
    Antoun
    Expert Essbase, BO, SQL

    La bible d'Essbase, 2ème édition

  9. #9
    Nouveau Candidat au Club
    Profil pro
    Inscrit en
    Décembre 2006
    Messages
    5
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Décembre 2006
    Messages : 5
    Points : 1
    Points
    1
    Par défaut
    Citation Envoyé par Antoun
    tu as essayé la mienne (avec le /s et en slurp mode) ?
    Non, ça ne marche pas, la difficulté est que je dois commencer la
    capture au 1er {{ et la continuer jusqu'au 1er }} sans tenir compte
    d'eventuels }} qui ne seraient pas les fermants du 1er {{ !

    Encore merci pour cette aide précieuse

  10. #10
    Rédacteur/Modérateur

    Avatar de Antoun
    Homme Profil pro
    Architecte décisionnel
    Inscrit en
    Octobre 2006
    Messages
    6 280
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 53
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Architecte décisionnel
    Secteur : Conseil

    Informations forums :
    Inscription : Octobre 2006
    Messages : 6 280
    Points : 11 736
    Points
    11 736
    Par défaut
    Citation Envoyé par Vovo2006
    Non, ça ne marche pas, la difficulté est que je dois commencer la
    capture au 1er {{ et la continuer jusqu'au 1er }} sans tenir compte
    d'eventuels }} qui ne seraient pas les fermants du 1er {{ !
    ah, toutes mes excuses, j'avais compris le contraire, que tu voulais seulement le niveau le + profond... ton exemple était pourtant clair, il faut que j'arrête la vodka !

    La solution est au chapitre "Perl", la section sur les parenthèses imbriquées à un niveau arbitraire, du bouquin de Friedl (Maîtrise des expressions régulières, chez O'Reilly), mais cela réclame une lecture approfondie dont je n'ai pas le temps...
    Antoun
    Expert Essbase, BO, SQL

    La bible d'Essbase, 2ème édition

  11. #11
    Expert éminent
    Avatar de Jedai
    Homme Profil pro
    Enseignant
    Inscrit en
    Avril 2003
    Messages
    6 245
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Côte d'Or (Bourgogne)

    Informations professionnelles :
    Activité : Enseignant

    Informations forums :
    Inscription : Avril 2003
    Messages : 6 245
    Points : 8 586
    Points
    8 586
    Par défaut
    Citation Envoyé par Vovo2006
    Je ne peux pas me baser sur la fin de ligne !
    Et je n'ai pas l'impression que &extract_bracketed fonctionne bien avec des
    délimiteurs doubles
    La bonne fonction est extract_tagged dans ton cas.

    Par ailleurs, il est peu raisonnable de tenter de résoudre la question par des regexs, en effet les regexs classiques sont incapable de traiter ce problème (le langage des parenthèses équilibrées n'est pas rationnel) et si les "regexs" de Perl en sont capable, ce serait uniquement en faisant appel à des techniques non standard, assez fragiles et complexes...
    A noter que Perl 6 permettra de faire ceci aisément.

    --
    Jedaï

  12. #12
    Nouveau Candidat au Club
    Profil pro
    Inscrit en
    Décembre 2006
    Messages
    5
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Décembre 2006
    Messages : 5
    Points : 1
    Points
    1
    Par défaut
    Merci à tous pour votre aide.
    Voici une façon de faire en numérotant les {{ et }}

    my $nested ;
    $entry =~ s/(\{\{|\}\})/(substr ($1,1,1) eq "\{") ?
    "\!" . ($nested++) . $1 :
    ($nested > 0) ? "\!" . (--$nested) . $1 : $1 /gxie ;
    while ($nested > 0)
    { $entry .= "\!" . (--$nested) . "\}\}" ; } # assume end of tag at end of text

    for (my $nested = 15 ; $nested >= 0 ; $nested--) # 30 is arbitrary upper limit for nested tags
    {
    $entry =~ s/\!$nested\{\{(.*?)\!$nested\}\}/&EntryReplaceMsgTag($1)/ge ;
    }

    $entry =~ s/\!\-?\d\{\{/\{\{/gi ; # clean up unmatched tags
    $entry =~ s/\!\-?\d\}\}/\}\}/gi ; # clean up unmatched tags

  13. #13
    Rédacteur/Modérateur

    Avatar de Antoun
    Homme Profil pro
    Architecte décisionnel
    Inscrit en
    Octobre 2006
    Messages
    6 280
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 53
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Architecte décisionnel
    Secteur : Conseil

    Informations forums :
    Inscription : Octobre 2006
    Messages : 6 280
    Points : 11 736
    Points
    11 736
    Par défaut
    Bravo ! je me note ça dans un coin pour le jour où j'en aurai besoin !
    Antoun
    Expert Essbase, BO, SQL

    La bible d'Essbase, 2ème édition

Discussions similaires

  1. MCD: Trouver les bonnes associations
    Par mymemorial dans le forum Merise
    Réponses: 4
    Dernier message: 06/03/2013, 12h32
  2. [MCD] comment trouver les bonnes entités et les cardinalités ?
    Par jakol dans le forum Schéma
    Réponses: 1
    Dernier message: 08/11/2009, 18h42
  3. Réponses: 6
    Dernier message: 27/02/2008, 00h01
  4. [VS 2003]Trouver l'accolade fermante correspondante
    Par soazig dans le forum Visual C++
    Réponses: 7
    Dernier message: 21/11/2007, 14h10
  5. Toutes les bonnes choses ont un début ...
    Par Bols2000 dans le forum Algorithmes et structures de données
    Réponses: 4
    Dernier message: 22/08/2002, 17h01

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