web-dev-qa-db-fra.com

Comment faire référence à la valeur de nœud actuelle dans XSL pour chaque test?

Disons que j'ai un document XML comme celui-ci:

<books>
    <book>1110</book>
    <book>1111</book>
    <book>1112</book>
    <book>1113</book>
</books>

J'essaie de configurer une condition qui teste la valeur du nœud actuel dans le for-each, mais je fais quelque chose de mal:

<xsl:for-each select="/books/book">
    <xsl:if test=".[='1112']">
        Success
    </xsl:if>
</xsl:for-each>

Qu'est-ce que je fais mal?

27
David

L'utilisation de . Peut en effet faire référence au nœud actuel (ou "context"), mais pas à la façon dont vous l'utilisez ici. Dans XPath, .[foo] N'est pas une syntaxe valide - vous devez utiliser self::node()[foo] à la place. De plus, l'opérateur = A besoin de quelque chose pour correspondre, dans ce cas, le sélecteur text() pour accéder au contenu texte de l'élément:

<xsl:for-each select="/books/book">
    <xsl:if test="self::node()[text()='1112']">
        Success
    </xsl:if>
</xsl:for-each>

Comme indiqué dans les autres réponses, cependant, à moins que votre for-each N'effectue également d'autres opérations, vous n'avez pas besoin de répéter du tout et vous pouvez utiliser simplement if pour accomplir la même tâche:

<xsl:if test="/books/book[. = 1112]">
    Success
</xsl:if>
41
Ben Blank

J'essaie de configurer une condition qui teste la valeur du nœud actuel dans le for-each, mais je fais quelque chose de mal:

La première chose qui est incorrecte est la syntaxe:

   .[='1112']

Il y a deux choses qui ne vont pas ici:

  1. Dans [et] il n'y a pas de prédicat: l'opérateur "=" a besoin de deux arguments mais un seul est fourni.

  2. .[x = y] Est toujours une syntaxe non valide, bien que le prédicat soit OK. Cela doit être spécifié comme:

    self :: node () [condition]

La deuxième chose dans le code fourni qui peut être amélioré est l'instruction <xsl:for-each>, Qui n'est pas du tout nécessaire; Une seule expression XPath sera suffisante.

Pour résumer, une expression XPath possible qui évalue à la valeur booléenne requise est:

   /books/book[. = '1112']

S'il est vraiment nécessaire que la condition soit testée dans l'instruction <xsl:for-each>, alors une expression XPath correcte que j'utiliserais est:

   . = '1112'

Ce qui précède est une comparaison de chaînes et peut ne pas correspondre à true() s'il y a des espaces autour. Par conséquent, ne comparaison numérique peut être meilleure:

  . = 1112
13
Dimitre Novatchev

Bien que Ben ait répondu correctement à votre question, l'utilisation de for-each est certainement la mauvaise approche générale. Après tout, c'est XSLT. Donc, vous recherchez probablement plus quelque chose comme ça:

<xsl:if test="/books/book[text()='1112']">
  Success
</xsl:if>
3
tcurdt

XSLT a une fonction spécialement pour ce problème.

http://www.w3.org/TR/xslt#function-current

3
Dominic Cronin

Essayez avec ça

<xsl:for-each select="/books/book">
    <xsl:if test="current() = '1112'">
        Success
    </xsl:if> 
</xsl:for-each>
1
Shaiful Islam