Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/xslt/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何使用XSL遍历基于变量的xml文件_Xml_Xslt - Fatal编程技术网

如何使用XSL遍历基于变量的xml文件

如何使用XSL遍历基于变量的xml文件,xml,xslt,Xml,Xslt,我最近问了一个问题,关于哪个引擎来解析我的xml,并决定坚持使用XSL,但我只能完成一半的工作。参考: 我已经尽力穿越了->->,但是任何一个在nav下的孩子和我的逻辑都被搞砸了 问题是,当@path是下一个子节点层时,如何在xsl中重复我的逻辑以深入xml子节点 我做得对吗?我觉得我遗漏了一些东西,应该以某种方式使用模板 例如,这里是我的xsl样式表 <?xml version="1.0" encoding="UTF-8"?> <!-- Document : si

我最近问了一个问题,关于哪个引擎来解析我的xml,并决定坚持使用XSL,但我只能完成一半的工作。参考:

我已经尽力穿越了->->,但是任何一个在nav下的孩子和我的逻辑都被搞砸了

问题是,当@path是下一个子节点层时,如何在xsl中重复我的逻辑以深入xml子节点

我做得对吗?我觉得我遗漏了一些东西,应该以某种方式使用模板

例如,这里是我的xsl样式表

<?xml version="1.0" encoding="UTF-8"?>
<!--
    Document   : sitemap.xsl
    Created on : 2 February 2011, 14:53
    Author     : Jared
    Description:
        Purpose of transformation follows.
-->
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="html" />
    <xsl:param name="page" select="default"/>

    <xsl:template match="root">
        <ul class="level-0 top-level">
            <xsl:for-each select="*/nav">
                <xsl:choose>
                    <xsl:when test="$page = '/index.aspx'">
                        <!-- level 0 -->
                        <li>
                            <a><xsl:attribute name="href"><xsl:value-of select="@path" /></xsl:attribute><xsl:value-of select="@name" /></a>
                        </li>
                    </xsl:when>

                    <xsl:when test="@path=$page and $page != '/index.aspx'">
                        <!-- level 2 -->
                        <li class="children-open current-menu-page">
                            <a><xsl:attribute name="href"><xsl:value-of select="@path" /></xsl:attribute><xsl:value-of select="@name" /></a>
                            <ul class="level-2 current-menu">
                                <xsl:for-each select="/root/menu/nav[@path=$page]/child::*">
                                    <li>
                                        <a><xsl:attribute name="href"><xsl:value-of select="@path" /></xsl:attribute><xsl:value-of select="@name" /><br /></a>
                                    </li>
                                </xsl:for-each>
                            </ul>
                        </li>
                    </xsl:when>


                    <xsl:otherwise>
                        <li>
                            <a><xsl:attribute name="href"><xsl:value-of select="@path" /></xsl:attribute><xsl:value-of select="@name" /></a>
                        </li>
                    </xsl:otherwise>


                </xsl:choose>

            </xsl:for-each>

        </ul>
    </xsl:template>

</xsl:stylesheet>
XML文件如下所示:

<root name="menutest">
  <menu>
      <nav name="home" path="index.php" />

      <nav name="menulink1" path="link1.php">
          <nav name="menulink1child1" path="menulink1childlink1.php">
             <nav name="menulink1child1child1"
                  path="menulink1childlink1childlink1.php" />
          </nav>
      </nav>

      <nav name="menulink2" path="link2.php">
         <nav name="menulink1child2" path="menulink2childlink2.php">
            <nav name="menulink2child2child2"
                 path="menulink2childlink2childlink2.php" />
         </nav>
      </nav>

      <nav name="menulink3" path="link3.php">
         <nav name="menulink3child3" path="menulink3childlink3.php">
             <nav name="menulink3child3child3"
                  path="menulink3childlink3childlink3.php" />
         </nav>
      </nav>

      <nav name="menulink4" path="link4.php">
         <nav name="menulink4child4"
              path="menulink4childlink4.php">
             <nav name="menulink4child4child4"
               path="menulink4childlink4childlink4.php" />
         </nav>
      </nav>
  </menu>
</root>
这基本上只显示基于param$page的第一层子级。 菜单如何工作以及选择哪些节点的示例,基本对齐的节点是子节点,缩进的节点是父节点的子节点等等

短暂性脑缺血发作 贾里德

更新的代码片段

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="html" />
    <xsl:param name="page" select="'index.aspx'"/>

    <xsl:template name="makeUL">
        <ul class="level-2 current-menu">
            <xsl:apply-templates/>
        </ul>
    </xsl:template>
    <xsl:template match="nav">

            <li>
            <xsl:if test=".//@path = $page and $page != '/index.aspx'">
                <xsl:attribute name="class"><xsl:text>children-open current-menu-page</xsl:text></xsl:attribute>
             </xsl:if>
            <a href="{@path}">
                <xsl:value-of select="@name" />
            </a>
            <xsl:if test=".//@path = $page and $page != '/index.aspx'">
                 <xsl:call-template name="makeUL"/>
            </xsl:if>
        </li>

    </xsl:template>
</xsl:stylesheet>
在xml解析之前,我还回显了ul,但我可能有错误:

echo '<ul class="level-0 top-level">'."\n\r";
    echo $xsl->transformToXML($dom);
echo '</ul>'."\n\r";

问题的根本原因是您试图使用拉式处理—传统的构造,如xsl:for-each和xsl:choose,而不是使用模板规则和xsl:apply-templates以XSLT方式编写。通常可以用拉式风格编写代码,但专家们避免了这种做法,因为它往往会让您陷入这种麻烦


我通常这么说,但有一种情况是不可能的,那就是输入数据是nav元素中的递归nav元素,无限嵌套。您只能使用递归代码处理递归数据,在这种情况下,apply templates风格的编码变得至关重要。坐下来阅读教程,阅读一些示例,直到您理解了这个概念,然后在编码中使用它。

问题的根本原因是您试图使用拉式处理—传统的构造,如xsl:for each和xsl:choose,而不是使用模板规则和xsl:apply模板以XSLT方式编写。通常可以用拉式风格编写代码,但专家们避免了这种做法,因为它往往会让您陷入这种麻烦


我通常这么说,但有一种情况是不可能的,那就是输入数据是nav元素中的递归nav元素,无限嵌套。您只能使用递归代码处理递归数据,在这种情况下,apply templates风格的编码变得至关重要。坐下来阅读教程并阅读一些示例,直到您理解了概念,然后在编码中使用它。

如果您想展开包含已识别节点的树分支,此样式表:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="html" />
    <xsl:param name="page" select="'menulink1childlink1.php'"/>
    <xsl:template match="menu" name="makeUL">
        <ul>
            <xsl:apply-templates/>
        </ul>
    </xsl:template>
    <xsl:template match="nav">
        <li>
            <a href="{@path}">
                <xsl:value-of select="@name" />
            </a>
            <xsl:if test=".//@path = $page">
                <xsl:call-template name="makeUL"/>
            </xsl:if>
        </li>
    </xsl:template>
</xsl:stylesheet>
输出:

<ul>
    <li><a href="index.php">home</a></li>
    <li><a href="link1.php">menulink1</a>
        <ul>
            <li><a href="menulink1childlink1.php">menulink1child1</a>
                <ul>
                    <li><a href="menulink1childlink1childlink1.php"
                          >menulink1child1child1</a></li>
                </ul>
            </li>
        </ul>
    </li>
    <li><a href="link2.php">menulink2</a></li>
    <li><a href="link3.php">menulink3</a></li>
    <li><a href="link4.php">menulink4</a></li>
</ul>
呈现:

家 menulink1 菜单1 Menulink1儿童1儿童1 menulink2 menulink3 menulink4
注意:这是唯一一种使用//缩写的情况。

如果要展开包含已识别节点的树分支,此样式表:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="html" />
    <xsl:param name="page" select="'menulink1childlink1.php'"/>
    <xsl:template match="menu" name="makeUL">
        <ul>
            <xsl:apply-templates/>
        </ul>
    </xsl:template>
    <xsl:template match="nav">
        <li>
            <a href="{@path}">
                <xsl:value-of select="@name" />
            </a>
            <xsl:if test=".//@path = $page">
                <xsl:call-template name="makeUL"/>
            </xsl:if>
        </li>
    </xsl:template>
</xsl:stylesheet>
输出:

<ul>
    <li><a href="index.php">home</a></li>
    <li><a href="link1.php">menulink1</a>
        <ul>
            <li><a href="menulink1childlink1.php">menulink1child1</a>
                <ul>
                    <li><a href="menulink1childlink1childlink1.php"
                          >menulink1child1child1</a></li>
                </ul>
            </li>
        </ul>
    </li>
    <li><a href="link2.php">menulink2</a></li>
    <li><a href="link3.php">menulink3</a></li>
    <li><a href="link4.php">menulink4</a></li>
</ul>
呈现:

家 menulink1 菜单1 Menulink1儿童1儿童1 menulink2 menulink3 menulink4
注:这是唯一一种使用//缩写的情况。

这是非常不清楚的。请提供一个完整但最少的示例:源XML文档、完整的所需结果以及转换必须实现的任何规则。@Dimitre Novatchev,您好Dimitre,感谢您花时间研究我的问题,我已经用更多的示例对其进行了更新,希望这能让事情变得更清楚。蒂娅,我不太清楚你想要什么。是否要展开已标识节点的分支?@Alejandro是的,是的,我要基于param展开节点,param是子节点的@path属性。我认为您的回答让我走上了正确的道路,尽管正如@michaelkay指出的,我想用xslt的方式来做。谢谢你们帮我,这还不清楚。请提供一个完整但最少的示例:源XML文档、完整的所需结果以及转换必须实现的任何规则。@Dimitre Novatchev,您好Dimitre,感谢您花时间研究我的问题,我已经用更多的示例对其进行了更新,希望这能让事情变得更清楚。蒂娅,我不太清楚你想要什么。是否要展开已标识节点的分支?@Alejandro是的,是的,我要基于param展开节点,param是子节点的@path属性。我认为您的回答让我走上了正确的道路,尽管正如@michaelkay指出的,我想用xslt的方式来做。谢谢你们帮了我。@Alejandro谢谢,就这样做了,我已经包括了对代码片段的更新,这样你们就可以看到我在做什么了。“你现在把我引向了正确的方向,所以我觉得我现在可以完成这个任务了,tyvm”。@Jared:我没有添加这些@class,因为它不清楚。
应该是:第一个ul 0级顶级,每隔一个2级当前菜单;li在开放分支包括祖先儿童开放当前菜单页面?@Alejandro yup第一级ul为0级,如果我不清楚,我很抱歉,显然我太清楚了,无法正确解释:第二级儿童ul应为2级,等等。但是你的回答真的很有帮助,我想我可以处理剩下的,除非你想在你的原始答案中添加一些东西,tyvm:@Alejandro谢谢,就这样做了,我已经包括了对代码片段的更新,这样你就可以看到我在尝试做什么。“你现在把我引向了正确的方向,所以我觉得我现在可以完成这个任务了,tyvm”。@Jared:我没有添加这些@class,因为它不清楚。应该是:第一个ul 0级顶级,每隔一个2级当前菜单;li在开放分支包括祖先儿童开放当前菜单页面?@Alejandro yup第一级ul为0级,如果我不清楚,我很抱歉,显然我太清楚了,无法正确解释:第二级儿童ul应为2级,等等。但是你的回答真的很有帮助,我想我可以处理剩下的问题,除非你想在原来的答案中添加一些东西,tyvm: