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

XSL/XSLT/XPATH XML Discussion :

Boucle de lettres simples et multiples [XSLT 2.0]


Sujet :

XSL/XSLT/XPATH XML

  1. #1
    Candidat au Club
    Homme Profil pro
    Ingénieur d'études BDD textuelles
    Inscrit en
    Mars 2011
    Messages
    2
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Indre et Loire (Centre)

    Informations professionnelles :
    Activité : Ingénieur d'études BDD textuelles
    Secteur : Communication - Médias

    Informations forums :
    Inscription : Mars 2011
    Messages : 2
    Points : 4
    Points
    4
    Par défaut Boucle de lettres simples et multiples
    Bonjour,

    J'essaie de rédiger un script afin de générer à partir d'une collation d'ouvrage la liste de toutes les signatures.

    Exemple de fichier d'entrée:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    <?xml version="1.0" encoding="UTF-8"?>
    <xml>A-Z4 Aa-Zz2 AAa-SSs4<xml>
    Résultat souhaité de sortie :
    A4
    B4
    C4
    ... (etc)
    Z4
    Aa2
    Bb2
    ... (etc)
    Zz2
    AAa4
    ... (etc)
    SSs4


    Je suis parti de la solution fournie sur ce site en l'adaptant à mes besoins :
    http://xmlfr.org/listes/xml-tech/2005/07/0067.html


    Pour résumer, j'ai effectué un premier passage pour obtenir l'arbre suivant :

    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
     
    <?xml version="1.0" encoding="UTF-8"?>
    <?xml-stylesheet type="text/xsl" href="collation-to-excel2.xsl"?>
    <xml>
            <cahier>
                <lettre>ã</lettre>-<lettre>ĩ</lettre><nb>4</nb>
            </cahier>
            <cahier>
                <lettre>A</lettre>-<lettre>Z</lettre><nb>4</nb>
            </cahier>
            <cahier>
                <lettre>Aa</lettre>-<lettre>Zz</lettre><nb>4</nb>
            </cahier>
            <cahier>
                <lettre>AAa</lettre>-<lettre>SSs</lettre><nb>4</nb>
           </cahier>
    </xml>
    Et voici la XSL modifiée que j'applique et qui me pose problème :

    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
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
     
    <?xml version="1.0" encoding="UTF-8"?>
    <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
        xmlns:xs="http://www.w3.org/2001/XMLSchema"
        exclude-result-prefixes="xs"
        version="2.0">
     
    <xsl:template match="xml">
             <xml><xsl:apply-templates/></xml>
         </xsl:template>
     
     
        <!--Pour créer les signatures-->
     
     
        <xsl:template match="cahier">
           <xsl:call-template name="boucle">
                <xsl:with-param name="debut"><xsl:value-of select="descendant::lettre[1]"/></xsl:with-param>
                <xsl:with-param name="fin"><xsl:value-of select="descendant::lettre[last()]"/></xsl:with-param>
            </xsl:call-template>
        </xsl:template>
        <xsl:template name="boucle">
            <xsl:param name="debut">ã</xsl:param>
            <xsl:param name="fin">z</xsl:param>
            <xsl:param name="lettres">ãẽĩõabcdefghiklmnopqrstvxyz</xsl:param>
     
     
     
            <cahier><lettre><xsl:value-of select="$debut"/></lettre><nb><xsl:value-of select="descendant::nb[last()]"/></nb><xsl:text>
                </xsl:text></cahier>
     
     
            <xsl:variable name="position"
                select="string-length(substring-before($lettres, $debut)) + 1"/>
            <xsl:variable name="suivant" select="substring($lettres, $position +
                1, 1)"/>
            <xsl:if test="$suivant != '' and $debut != $fin">
                <xsl:call-template name="boucle">
                    <xsl:with-param name="debut" select="$suivant"/>
                    <xsl:with-param name="fin" select="$fin"/>
                    <xsl:with-param name="lettres" select="$lettres"/>
                </xsl:call-template>
            </xsl:if>
    </xsl:template>
    </xsl:stylesheet>

    Cela fonctionne bien lorsqu'on n'a qu'une lettre mais évidemment pas lorsqu'il y en a plusieurs.

    J'ai tenté pas mal de chose (analyse-string, distinguer les unités de $lettres avec des séparateurs, etc) mais je suis bloqué par la syntaxe avec les variables dans la déclaration de la variable position :/

  2. #2
    Membre émérite
    Avatar de polymorphisme
    Homme Profil pro
    Publishing
    Inscrit en
    Octobre 2009
    Messages
    1 460
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 50
    Localisation : France, Gironde (Aquitaine)

    Informations professionnelles :
    Activité : Publishing
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Octobre 2009
    Messages : 1 460
    Points : 2 371
    Points
    2 371
    Par défaut
    Bonjour,

    Cela fonctionne bien lorsqu'on n'a qu'une lettre mais évidemment pas lorsqu'il y en a plusieurs.
    Oui parce tu n'a pas vu que tu pouvais compter le nombre de lettres, par exemple AAa contient 3 lettres.

    Pour écrire :
    tu n'a besoin de connaître que la lettre S et le nombre de lettres 3.

    Dit autrement, puisque tu sais obtenir :
    et que tu connais le nombre de lettres : 3.
    Tu n'aura pas difficulté à obtenir :

  3. #3
    Candidat au Club
    Homme Profil pro
    Ingénieur d'études BDD textuelles
    Inscrit en
    Mars 2011
    Messages
    2
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Indre et Loire (Centre)

    Informations professionnelles :
    Activité : Ingénieur d'études BDD textuelles
    Secteur : Communication - Médias

    Informations forums :
    Inscription : Mars 2011
    Messages : 2
    Points : 4
    Points
    4
    Par défaut
    Oui, j'y ai pensé après coup.

    Je suis finalement parti sur l'idée d'effectuer des tests sur le contenu des <lettre> en fonction du nombre de lettre et en coupant au 1er caractère afin d'entrer dans le moule de mes params. Ensuite, je recompose le contenu.
    Cela m'a ainsi permis de gérer la recomposition de la casse (si plus d'une lettre, l'ensemble est en majuscule sauf la dernière) avec une autre variable lettres2 et un translate.

    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
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
     
    <?xml version="1.0" encoding="UTF-8"?>
    <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
        xmlns:xs="http://www.w3.org/2001/XMLSchema"
        exclude-result-prefixes="xs"
        version="2.0">
     
    <xsl:template match="xml">
             <xml><xsl:apply-templates/></xml>
         </xsl:template>
     
     
        <!--Pour créer les signatures-->
     
     
        <xsl:template match="cahier">
           <xsl:call-template name="boucle">
                <xsl:with-param name="debut"><xsl:value-of select="descendant::lettre[1]"/></xsl:with-param>
                <xsl:with-param name="fin"><xsl:value-of select="descendant::lettre[last()]"/></xsl:with-param>
            </xsl:call-template>
        </xsl:template>
        <xsl:template name="boucle">
            <xsl:param name="debut">ã</xsl:param>
            <xsl:param name="fin">z</xsl:param>
            <xsl:param name="lettres">ãẽĩõabcdefghiklmnopqrstvxyz</xsl:param>
            <xsl:param name="lettres2">ABCDEFGHIKLMNOPQRSTVXYZ</xsl:param>
     
            <xsl:variable name="majuscules">ABCDEFGHIJKLMNOPQRSTUVWXYZ</xsl:variable>
            <xsl:variable name="minuscules">abcdefghijklmnopqrstuvwxyz</xsl:variable>
     
            <cahier><lettre><xsl:value-of select="$debut"/></lettre><nb><xsl:value-of select="descendant::nb[last()]"/></nb><xsl:text>
                </xsl:text></cahier>
     
     
            <xsl:choose>
                <xsl:when test="matches($debut,'^.$')">
                    <xsl:variable name="debut2" select="$debut"/>
                <xsl:variable name="position" select="string-length(substring-before($lettres, $debut2)) + 1"/>
                    <xsl:variable name="suivant">
                        <xsl:value-of select="substring($lettres, $position +1, 1)"/>
                    </xsl:variable>
                    <xsl:if test="$suivant != '' and $debut2 != $fin">
                    <xsl:call-template name="boucle">
                        <xsl:with-param name="debut" select="$suivant"/>
                        <xsl:with-param name="fin" select="$fin"/>
                        <xsl:with-param name="lettres" select="$lettres"/>
                    </xsl:call-template>
                </xsl:if>
                </xsl:when>
     
                <xsl:when test="matches($debut,'^..$')">
                    <xsl:variable name="debut2" select="substring($debut,1,1)"/>
                    <xsl:variable name="position" select="string-length(substring-before($lettres2, $debut2)) + 1"/>
                    <xsl:variable name="suivant">
                        <xsl:value-of select="substring($lettres2, $position +1, 1)"/>
                        <xsl:value-of select="translate(substring($lettres2, $position +1, 1),$majuscules,$minuscules)"/>
                    </xsl:variable>
                    <xsl:if test="$suivant != '' and $debut2 != $fin">
                        <xsl:call-template name="boucle">
                            <xsl:with-param name="debut" select="$suivant"/>
                            <xsl:with-param name="fin" select="$fin"/>
                            <xsl:with-param name="lettres" select="$lettres2"/>
                        </xsl:call-template>
                    </xsl:if>
                </xsl:when>
     
                <xsl:when test="matches($debut,'^...$')">
                    <xsl:variable name="debut2" select="substring($debut,1,1)"/>
                    <xsl:variable name="position" select="string-length(substring-before($lettres2, $debut2)) + 1"/>
                    <xsl:variable name="suivant">
                        <xsl:value-of select="substring($lettres2, $position +1, 1)"/>
                        <xsl:value-of select="substring($lettres2, $position +1, 1)"/>
                        <xsl:value-of select="translate(substring($lettres2, $position +1, 1),$majuscules,$minuscules)"/>
                    </xsl:variable>
                    <xsl:if test="$suivant != '' and $debut2 != $fin">
                        <xsl:call-template name="boucle">
                            <xsl:with-param name="debut" select="$suivant"/>
                            <xsl:with-param name="fin" select="$fin"/>
                            <xsl:with-param name="lettres" select="$lettres2"/>
                        </xsl:call-template>
                    </xsl:if>
                </xsl:when>
            </xsl:choose>
    </xsl:template>
    </xsl:stylesheet>
    Je suppose qu'il y aurait un autre moyen peut-être plus propre avec la fonction count mais cela me semble plus compliqué avec mes moyens et ça marche en l'état

    Merci !

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

Discussions similaires

  1. [XL-2010] Boucles imbriquées très simples : ne fonctionne pas
    Par funkyspirit dans le forum Macros et VBA Excel
    Réponses: 2
    Dernier message: 24/02/2012, 11h58
  2. [Débutant] probleme sur boucle et pas simple
    Par biboulou dans le forum VB.NET
    Réponses: 3
    Dernier message: 14/02/2012, 00h45
  3. Regression simple et multiple
    Par couanp dans le forum MATLAB
    Réponses: 3
    Dernier message: 24/05/2007, 10h31
  4. Réponses: 6
    Dernier message: 31/08/2005, 17h27
  5. [Swing][boucles] for, do, if .....comment faire simple?
    Par chastel dans le forum AWT/Swing
    Réponses: 7
    Dernier message: 02/05/2004, 22h49

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