测验中的 XSLT 1.0 select 个元素 XML

XSLT 1.0 select elements in Quiz XML

这是一个示例 XML。

<Root>
  <Story>
    <body>
      <quiz>1</quiz>How to select that rightanswer from another Story ?
    </body>
    <answer>answer1-1</answer>
    <answer>answer1-2</answer>
    <answer>answer1-3</answer>
    <body>
      <quiz>2</quiz>And how to push these <qitem/>s into <qitems/> ?
    </body>
    <answer>answer2-1</answer>
    <answer>answer2-2</answer>
    <answer>answer2-3</answer>
    <answer>answer2-4</answer>
  </Story>
  <Story>
    <h3>RIGHT_ANSWERS</h3>
    <rightanswer>
      RightAnswer1 IDK
    </rightanswer>
    <rightanswer>
      RightAnswer2 IDK
    </rightanswer>
  </Story>
</Root>

预期输出:

<Root>
    <Story>
        <quiz>
            <qitems>
                <qitem>
                    <question>
                        <qtitle>1</qtitle>
                        <qtext>How to select that rightanswer from another Story ?</qtext>
                    </question>
                    <answers>
                        <answer>answer1-1</answer>
                        <answer>answer1-2</answer>
                        <answer>answer1-3</answer>
                    </answers>
                    <rightanswer>RightAnswer1 IDK</rightanswer>
                </qitem>
                <qitem>
                    <question>
                        <qtitle>2</qtitle>
                        <qtext>And how to push these <qitem/>s into <qitems/> ?</qtext>
                    </question>
                    <answers>
                        <answer>answer2-1</answer>
                        <answer>answer2-2</answer>
                        <answer>answer2-3</answer>
                        <answer>answer2-4</answer>
                    </answers>
                    <rightanswer>RightAnswer2 IDK</rightanswer>
                </qitem>
            </qitems>
        </quiz>
    </Story>
</Root>

我所能做的就是将每个 body[quiz] 及其以下名为 answer 的兄弟姐妹放入 <qitem> 元素中,然后将这些 <qitem>s 推入父元素<qitems> 并选择 <rightanswer>。到目前为止我有这个 xsl:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"  version="1.0">
    <xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes" />
    <xsl:strip-space elements="*" />
    <xsl:template match="node()|@*">
        <xsl:copy>
            <xsl:apply-templates select="node()|@*"/>
        </xsl:copy>
    </xsl:template>
    <xsl:template match="body[quiz]" >
        <qitem>
            <question>          
                <qtitle>
                    <xsl:value-of select="quiz" />
                </qtitle>
                <qtext>
                    <xsl:apply-templates select="node()" />
                </qtext>
            </question>
            <answers>
                <xsl:apply-templates select="following-sibling::*[1][self::answer]" mode="following" />
            </answers>
            <rightanswer></rightanswer>
        </qitem>
    </xsl:template>
    <xsl:template match="answer" mode="following">
        <answer>
            <xsl:apply-templates select="node()" />
        </answer>
        <xsl:apply-templates select="following-sibling::*[1][self::answer]" mode="following" />
    </xsl:template>

    <xsl:template match="body/quiz" />
    <xsl:template match="answer" />
    <xsl:template match="h3"/>
</xsl:stylesheet>

看看这个:http://xsltransform.net/nc4NzQr

如果可以假设 Root 元素总是恰好包含 2 个 Story 元素,一个包含问答,一个包含正确答案,那么您可以简单地做:

XSLT 1.0

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" version="1.0" encoding="utf-8" indent="yes"/>
<xsl:strip-space elements="*"/>

<!-- identity transform -->
<xsl:template match="@*|node()">
    <xsl:copy>
        <xsl:apply-templates select="@*|node()"/>
    </xsl:copy>
</xsl:template>

<xsl:template match="Story[1]"> 
    <qitems>
        <xsl:apply-templates select="body"/>
    </qitems>
</xsl:template>

<xsl:template match="body">
    <xsl:variable name="i" select="position()" />
    <qitem>
        <question>          
            <qtitle>
                <xsl:value-of select="quiz" />
            </qtitle>
            <qtext>
                <xsl:apply-templates/>
            </qtext>
        </question>
        <answers>
            <xsl:apply-templates select="following-sibling::answer[1]" mode="following"/>
        </answers>
        <xsl:apply-templates select="following::Story/rightanswer[$i]"/>
    </qitem>
</xsl:template>

<!-- sibling  recursion -->       
<xsl:template match="answer" mode="following">
    <answer>
        <xsl:apply-templates/>
    </answer>
    <xsl:apply-templates select="following-sibling::*[1][self::answer]" mode="following" />
</xsl:template>

<xsl:template match="Story[2]" />
<xsl:template match="quiz" /> 

</xsl:stylesheet>

got stuck on pushing these <qitem>s into parent <qitems>

我不明白为什么你需要 <qitems> 包装器以及它代表什么;在我看来,您请求的输出中已经有太多包装元素。在上面的示例中,我让 <qitems> 代表父级 Story 并删除了 Story 包装器本身。