0

我有以下要转换的 xml 数据结构:

<root>
        <main1>
            <page>
                <text-body>
                    <title>K1</title>
                    <subtitle>Text</subtitle>
                </text-body>
                <text-body>
                    <title>Text</title>
                    <subtitel>Text</subtitel>
                </text-body>
                <text-body>
                    <title>Text</title>
                    <subtitel>Text</subtitel>
                </text-body>
            </page>
            <page>
                <text-body>
                    <title>K2</title>
                    <subtitel>Text</subtitel>
                </text-body>
                <text-body>
                    <title>Text</title>
                    <subtitel>Text</subtitel>
                </text-body>
            </page>
            <page>
                <text-body>
                    <title>K3</title>
                    <subtitel>Text</subtitel>
                </text-body>
                <text-body>
                    <title>Text</title>
                    <subtitel>Text</subtitel>
                </text-body>
            </page>
        </main1>
        <main2>
            <text-body>
                <title>B</title>
                <subtitle>B</subtitle>
                <body>B</body>
            </text-body>
            <text-body>
                <title>C</title>
                <subtitle>C</subtitle>
                <body>C</body>
            </text-body>
            <text-body>
                <title>D</title>
                <subtitle>D</subtitle>
                <body>D</body>
            </text-body>
        </main2>
 </root>

我需要用 main2/text-body 中的数据替换 main1/text-body 中的数据为标题 K1、K2、K3,但保留 main1 中的其他 text-body 元素。输出应如下所示:

<root>
        <main1>
            <page>
                <text-body>
                    <title>B</title>
                    <subtitle>B</subtitle>
                    <body>B</body>
                </text-body>
                <text-body>
                    <title>Text</title>
                    <subtitel>Text</subtitel>
                </text-body>
                <text-body>
                    <title>Text</title>
                    <subtitel>Text</subtitel>
                </text-body>
            </page>
            <page>
                <text-body>
                    <title>C</title>
                    <subtitle>C</subtitle>
                    <body>C</body>
                </text-body>
                <text-body>
                    <title>Text</title>
                    <subtitel>Text</subtitel>
                </text-body>
            </page>
            <page>
                <text-body>
                    <title>D</title>
                    <subtitle>D</subtitle>
                    <body>D</body>
                </text-body>
                <text-body>
                    <title>Text</title>
                    <subtitel>Text</subtitel>
                </text-body>
            </page>
        </main1>
        <main2>
            <text-body>
                <title>B</title>
                <subtitle>B</subtitle>
                <body>B</body>
            </text-body>
            <text-body>
                <title>C</title>
                <subtitle>C</subtitle>
                <body>C</body>
            </text-body>
            <text-body>
                <title>D</title>
                <subtitle>D</subtitle>
                <body>D</body>
            </text-body>
        </main2>
 </root>

我有以下 xsl 代码:

    <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0">
    <xsl:output method="xml"/>

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

        <xsl:template match="main1/page/text-body">
            <xsl:param name="count" select="title/substring(.,2,1)"/>
            <xsl:if test="title/substring(.,1,1)='K'">
               <xsl:copy-of select="/root/main2/text-body[$count]"/>
            </xsl:if>
        </xsl:template>

    </xsl:stylesheet>

我尝试选择标题中的数字并检查文本中是否有 K。但它不起作用。而且我不知道如何保留其他文本正文元素。这是当前的输出:

 <main1>
            <page>
                <text-body>
                <title>B</title>
                <subtitle>B</subtitle>
                <body>B</body>
            </text-body><text-body>
                <title>C</title>
                <subtitle>C</subtitle>
                <body>C</body>
            </text-body><text-body>
                <title>D</title>
                <subtitle>D</subtitle>
                <body>D</body>
            </text-body>


            </page>
            <page>
                <text-body>
                <title>B</title>
                <subtitle>B</subtitle>
                <body>B</body>
            </text-body><text-body>
                <title>C</title>
                <subtitle>C</subtitle>
                <body>C</body>
            </text-body><text-body>
                <title>D</title>
                <subtitle>D</subtitle>
                <body>D</body>
            </text-body>

            </page>
            <page>
                <text-body>
                <title>B</title>
                <subtitle>B</subtitle>
                <body>B</body>
            </text-body><text-body>
                <title>C</title>
                <subtitle>C</subtitle>
                <body>C</body>
            </text-body><text-body>
                <title>D</title>
                <subtitle>D</subtitle>
                <body>D</body>
            </text-body>

            </page>
        </main1>
        <main2>
            <text-body>
                <title>B</title>
                <subtitle>B</subtitle>
                <body>B</body>
            </text-body>
            <text-body>
                <title>C</title>
                <subtitle>C</subtitle>
                <body>C</body>
            </text-body>
            <text-body>
                <title>D</title>
                <subtitle>D</subtitle>
                <body>D</body>
            </text-body>
        </main2>
 </root>

请帮忙!

4

2 回答 2

0

使用谓词仅匹配text-body您真正想要交换的元素。当您使用 XSLT 2.0 时,您可以在谓词中使用正则表达式:

<xsl:stylesheet version="2.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema">
  <xsl:output method="xml"/>

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

  <xsl:template match="main1/page/text-body[matches(title,'^K\d+$')]">
    <xsl:variable name="count" select="xs:integer(title/substring(.,2))"/>
    <xsl:copy-of select="/root/main2/text-body[$count]"/>
  </xsl:template>

</xsl:stylesheet>
于 2013-01-16T22:38:01.147 回答
0

主要问题是你的count参数设置为字符串,但是如果你想用in作为索引,它应该是一个数字,所以你需要这样做

<xsl:copy-of select="/root/main2/text-body[number($count)]"/>

此外,您可能不想在此处使用xsl:if ,因为对于您当前的模板,当 if 条件为 false 时,它​​不会输出text-body元素。您实际上应该将测试移动到模板匹配的一部分。

<xsl:template match="main1/page/text-body[title/substring(.,1,1)='K']">

这是完整的 XSLT

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0">
   <xsl:output method="xml"/>

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

   <xsl:template match="main1/page/text-body[title/substring(.,1,1)='K']">
      <xsl:param name="count" select="title/substring(.,2,1)"/>
      <xsl:copy-of select="/root/main2/text-body[number($count)]"/>
   </xsl:template>
</xsl:stylesheet>

这应该会产生您预期的输出。

如果您对不同的方法感兴趣,您可以选择定义一个xsl:key来查找main2/text-body元素

<xsl:key name="main2" 
     match="main2/text-body" 
     use="concat('K', count(preceding-sibling::text-body) + 1)" />

这样,您可以通过使用以下模板匹配main1/page/text-body元素来消除对子字符串的需求

 <xsl:template match="main1/page/text-body[key('main2', title)]">
    <xsl:copy-of select="key('main2', title)"/>
 </xsl:template>
于 2013-01-16T23:26:38.070 回答