子XML元素不使用XSLT移动

时间:2013-04-09 12:41:58

标签: xslt

我需要移动<sub><sup>元素,如输出中所示。我能够移动<sup>元素。子元素不动。我还需要将元素重命名为<msub><msup>。如果我运行两次XSLT,我就能得到输出。但我不想这样做。请纠正我错误的地方。我应该使用XSLT1.0

输入XML:

<?xml version='1.0' encoding='UTF-8' ?>
<chapter xmlns="http://www.w3.org/1998/Math/MathML">
    <math display="block">
        <mfenced>
            <mrow>
                <mfrac>
                    <mrow>
                        <mi>v</mi>
                        <sub>
                            <mrow><mi>n</mi></mrow>
                        </sub>
                    </mrow>
                    <mrow>
                        <mi>v</mi>
                        <sub>
                            <mrow><mi>d</mi></mrow>
                        </sub>
                    </mrow>
                </mfrac>
            </mrow>
        </mfenced>
        <sup><mrow><mn>2</mn></mrow></sup>
    </math>
</chapter>

示例XSLT尝试:

<?xml version='1.0'?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:m="http://www.w3.org/1998/Math/MathML" xmlns="http://www.w3.org/1998/Math/MathML" exclude-result-prefixes="m">

<xsl:output method="xml"/>
<xsl:template match="@* | node()">
<xsl:choose>
<xsl:when test="self::*/following-sibling::*[1]/self::m:sub"></xsl:when>
<xsl:when test="self::*/following-sibling::*[1]/self::m:sup"></xsl:when>
<xsl:when test="self::*/following-sibling::*[1]/self::m:subsup"></xsl:when>
<xsl:otherwise>
<xsl:copy>
<xsl:apply-templates select="@* | node()"/>
</xsl:copy>
</xsl:otherwise>
</xsl:choose>
</xsl:template>

<xsl:template match="m:sub">
<msub>
<xsl:copy-of select="self::*/preceding-sibling::*[1]"/>
<xsl:apply-templates/>
</msub>
</xsl:template>


<xsl:template match="m:subsup">
<msubsup>
<xsl:copy-of select="self::*/preceding-sibling::*[1]"/>
<xsl:apply-templates/>
</msubsup>
</xsl:template>

<xsl:template match="m:sup">
<msup>
<xsl:copy-of select="self::*/preceding-sibling::*[1]"/>
<xsl:apply-templates/>
</msup>
</xsl:template>
</xsl:stylesheet>

必需输出:

<?xml version='1.0' ?>
<chapter xmlns="http://www.w3.org/1998/Math/MathML">
<math display="block">
<msup>
    <mfenced>
        <mrow>
            <mfrac>
                <mrow>
                    <msub><mi>v</mi><mrow><mi>n</mi></mrow></msub>
                </mrow>
                <mrow>
                    <msub><mi>v</mi><mrow><mi>d</mi></mrow></msub>
                </mrow>
            </mfrac>
        </mrow>
    </mfenced>
    <mrow><mn>2</mn></mrow>
</msup>
</math>
</chapter>

3 个答案:

答案 0 :(得分:0)

当这个XSLT:

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet
  xmlns="http://www.w3.org/1998/Math/MathML"
  xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
  xmlns:m="http://www.w3.org/1998/Math/MathML"
  exclude-result-prefixes="m" version="1.0">
  <xsl:output omit-xml-declaration="no" indent="yes" />
  <xsl:strip-space elements="*" />

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

  <xsl:template match="m:mfenced">
    <msup>
      <mfenced>
        <xsl:apply-templates />
      </mfenced>
      <xsl:apply-templates select="following-sibling::m:sup/*" />
    </msup>
  </xsl:template>

  <xsl:template match="m:mfrac/m:mrow">
    <mrow>
      <msub>
        <xsl:apply-templates />
      </msub>
    </mrow>
  </xsl:template>

  <xsl:template match="m:sub">
    <xsl:apply-templates />
  </xsl:template>

  <xsl:template match="m:sup" />
</xsl:stylesheet>

...适用于提供的XML:

<?xml version="1.0" encoding="utf-8"?>
<chapter xmlns="http://www.w3.org/1998/Math/MathML">
  <math display="block">
    <mfenced>
      <mrow>
        <mfrac>
          <mrow>
            <mi>v</mi>
            <sub>
              <mrow>
                <mi>n</mi>
              </mrow>
            </sub>
          </mrow>
          <mrow>
            <mi>v</mi>
            <sub>
              <mrow>
                <mi>d</mi>
              </mrow>
            </sub>
          </mrow>
        </mfrac>
      </mrow>
    </mfenced>
    <sup>
      <mrow>
        <mn>2</mn>
      </mrow>
    </sup>
  </math>
</chapter>

...生成了想要的结果:

<?xml version="1.0"?>
<chapter xmlns="http://www.w3.org/1998/Math/MathML">
  <math display="block">
    <msup>
      <mfenced>
        <mrow>
          <mfrac>
            <mrow>
              <msub>
                <mi>v</mi>
                <mrow>
                  <mi>n</mi>
                </mrow>
              </msub>
            </mrow>
            <mrow>
              <msub>
                <mi>v</mi>
                <mrow>
                  <mi>d</mi>
                </mrow>
              </msub>
            </mrow>
          </mfrac>
        </mrow>
      </mfenced>
      <mrow>
        <mn>2</mn>
      </mrow>
    </msup>
  </math>
</chapter>

答案 1 :(得分:0)

如果我理解正确,你要做的就是

  1. 对于任何subsup元素,在元素内移动其先前的兄弟(如果有)
  2. sub重命名为msub,将sup重命名为msup
  3. 这个XSLT应该可以解决这个问题:

    <?xml version='1.0' encoding='UTF-8' ?>
    <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:m="http://www.w3.org/1998/Math/MathML" xmlns="http://www.w3.org/1998/Math/MathML" exclude-result-prefixes="m">
      <xsl:output method="xml"/>
    
      <xsl:template match="*[following-sibling::*[1]/self::m:sub]">
        <msub>
          <xsl:copy>
            <xsl:apply-templates select="@* | node()"/>
          </xsl:copy>
          <xsl:apply-templates select="following-sibling::*[1]/self::m:sub/@* | following-sibling::*[1]/self::m:sub/node()"/>
        </msub>
      </xsl:template>
    
      <xsl:template match="*[following-sibling::*[1]/self::m:sup]">
        <msup>
          <xsl:copy>
            <xsl:apply-templates select="@* | node()"/>
          </xsl:copy>
          <xsl:apply-templates select="following-sibling::*[1]/self::m:sup/@* | following-sibling::m:sup/node()"/>
        </msup>
      </xsl:template>
    
      <xsl:template match="m:sub | m:sup"></xsl:template>
    
      <xsl:template match="@* | node()">
        <xsl:copy>
          <xsl:apply-templates select="@* | node()"/>
        </xsl:copy>
      </xsl:template>
    
    </xsl:stylesheet>
    

    我唯一不清楚的是该怎么做subsup)没有先前兄弟的元素。上面的代码忽略了它们。

答案 2 :(得分:0)

Siva,您可以通过引入新模板阻止原始的“mi”输出:

&lt; xsl:template match =“m:mi”&gt;     &LT; XSL:如果       test =“not(name(follow-sibling :: [1])='sub')而不是(name(follow-sibling :: [1])='sup')而不是( name(follow-sibling :: * [1])='subsup')“&gt;       &LT; MI&GT;         &LT; XSL:适用的模板/&GT;       &LT; / MI&GT;     &LT; / XSL:如果&GT;   &LT; / XSL:模板&GT;