xsl:variable xsl:copy-of select

J'ai le code XML suivant:

<?xml version="1.0" encoding="UTF-8"?>
<XmlTest>
    <Pictures attr="Pic1">Picture 1</Pictures>
    <Pictures attr="Pic2">Picture 2</Pictures>
    <Pictures attr="Pic3">Picture 3</Pictures>
</XmlTest>

Tout ce XSL fait ce qu'on attend (sortie de l'attribut de la première photo):

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:template match="/XmlTest">
        <xsl:variable name="FirstPicture" select="Pictures[1]">
        </xsl:variable>
        <xsl:value-of select="$FirstPicture/@attr"/>
    </xsl:template>
</xsl:stylesheet>

Il ne semble pas possible de faire de même à l'intérieur de la déclaration de la variable à l'aide de xsl:copy-of:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" >
    <xsl:template match="/XmlTest">
        <xsl:variable name="FirstPicture">
            <xsl:copy-of select="Pictures[1]"/>
        </xsl:variable>
        <xsl:value-of select="$FirstPicture/@attr"/>
    </xsl:template>
</xsl:stylesheet>

Curieux:
Si je viens de sélectionner "$FirstPicture" au lieu de "$FirstPicture/@attr" dans le deuxième exemple, il génère le nœud de texte de l'Image 1 comme prévu...

Avant de vous tous me suggère de réécrire le code:
C'est juste un test simplifié, mon objectif est d'utiliser un modèle nommé pour sélectionner un nœud dans la variable FirstPicture et les réutiliser pour d'autres sélections.

J'espère que quelqu'un pourrait m'aider à comprendre le comportement ou pourrait me suggérer un bon moyen pour sélectionner un nœud avec du code qui pourrait être réutilisé facilement (la decission de nœud qui est le premier complexe dans mon application réelle). Merci.

Edit (merci à Martin Honnen):
C'est ma solution de travail exemple (qui utilise en outre un autre modèle pour sélectionner l'image nœud), en utilisant la MME processeur XSLT:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:msxsl="urn:schemas-microsoft-com:xslt"
    version="1.0">
    <xsl:template match="/XmlTest">
        <xsl:variable name="FirstPictureResultTreeFragment">
            <xsl:call-template name="SelectFirstPicture">
                <xsl:with-param name="Pictures" select="Pictures" />
            </xsl:call-template>
        </xsl:variable>
        <xsl:variable name="FirstPicture" select="msxsl:node-set($FirstPictureResultTreeFragment)/*"/>
        <xsl:value-of select="$FirstPicture/@attr"/>
        <!-- further operations on the $FirstPicture node -->
    </xsl:template>

    <xsl:template name="SelectFirstPicture">
        <xsl:param name="Pictures"/>
        <xsl:copy-of select="$Pictures[1]"/>
    </xsl:template>
</xsl:stylesheet>

Pas beau, qu'il est en XSLT 1.0 pas possible à la sortie d'un nœud directement à partir d'un modèle, mais avec la variable supplémentaire au moins, c'est pas impossible.

Pourquoi voulez-vous effectuer l'opération coûteuse de la copie d'un sous-arbre? L'attribut va être la même dans la copie, car il est dans l'original. Utilisez simplement les sélectionner la forme - il est beaucoup plus efficace. Et vous éviter les XSLT 1.0 restrictions associées résultat fragments d'arbres.
Pour mon exemple, vous êtes absolument droit et en sélectionnant l'complet de l'ensemble de nœuds seraient les frais généraux. Dans mon application, je ne veux pas de sélectionner un seul attribut, mais j'ai besoin de commettre de nouvelles opérations sur ce nœud comme la sélection de nœuds secondaires et l'appel à d'autres modèles. Et je veux l'utiliser à plusieurs endroits dans mon xsl sans duplication de code.

OriginalL'auteur Matthias Kientz | 2012-12-13