查找所有文本节点和兄弟节点

时间:2013-08-27 12:57:54

标签: xslt xslt-2.0

我需要找到所有文本节点并创建新的节点序列(参见输入/输出XML),如果有任何内联节点(文本节点的先前兄弟节点或后续兄弟节点),则将这些标签重命名为< ; x id =“XX”local-name ='tagName'> text here< / x>其中“local-name”值应该是该节点的名称。这些内联节点可以是任何内容,而不是特定的列表。任何指针/解决方案都将是一个很大的帮助。感谢。

XSLT 2.0版 XSLT处理器 - Saxon EE / HE 9.X.X.X

    <?xml version="1.0" encoding="utf-8"?>
    <concept id="001" xml:lang="en-us">
        <title id="002">Notice</title>
        <shortdesc id="003">This information U.S.A.</shortdesc>
        <conbody id="004">
            <p id="005">This product blah blah <companyname id="006">blah bla</companyname> No other
                warranty expressed or implied. </p>
            <p id="007">This supersedes all previous notices.</p>
            <section id="008">
                <title id="009">COPYRIGHT LICENSE:</title>
                <p id="010">This information contains <b id="011">in source language</b> , blah blah</p>
            </section>
        </conbody>
    </concept>

预期产出:

    <?xml version="1.0" encoding="UTF-8"?>
    <root>
        <trans-unit id="002">
            <source>Notice</source>
            <target>Notice</target>
        </trans-unit>
        <trans-unit id="003">
            <source>This information U.S.A.</source>
            <target>This information U.S.A.</target>
        </trans-unit>
        <trans-unit id="005">
            <source>This product blah blah <x id="006" local-name="companyname">blah bla</x> No other
                warranty expressed or implied. </source>
            <target>This product blah blah <x id="006" local-name="companyname">blah bla</x> No other
                warranty expressed or implied.</target>
        </trans-unit>
        <trans-unit id="007">
            <source>This supersedes all previous notices.</source>
            <target>This supersedes all previous notices.</target>
        </trans-unit>
        <trans-unit id="009">
            <source>COPYRIGHT LICENSE:</source>
            <target>COPYRIGHT LICENSE:</target>
        </trans-unit>
        <trans-unit id="010">
            <source>This information contains <x id="011" local-name="b">in source language</x> , blah
                blah</source>
            <target>This information contains <x id="011" local-name="b">in source language</x> , blah
                blah</target>
        </trans-unit>
    </root>

我正在尝试这样的事情:

        <xsl:template match="/">
           <root>
            <xsl:for-each select="//text()">
                <xsl:if test=".!='' or .!=' '">
                <xsl:choose>
                    <xsl:when test="not(following-sibling::node()) or not(preceding-sibling::node())">
                        <trans-unit>
                            <xsl:attribute name="id">
                                <xsl:value-of select="../@id"/>
                            </xsl:attribute>
                            <source>
                                <xsl:value-of select="."/>    
                            </source>
                            <target>
                                <xsl:value-of select="."/>    
                            </target>
                        </trans-unit>                    
                    </xsl:when>                
                </xsl:choose>
                </xsl:if>
            </xsl:for-each>   
             </root>

1 个答案:

答案 0 :(得分:1)

样式表

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

<xsl:output indent="yes"/>
<xsl:strip-space elements="*"/>

<xsl:template match="concept">
  <root>
    <xsl:apply-templates/>
  </root>
</xsl:template>

<xsl:template match="concept//*[text()[normalize-space()]]">
  <transunit id="{@id}">
    <source>
      <xsl:apply-templates/>
    </source>
    <target>
      <xsl:apply-templates/>
    </target>
  </transunit>
</xsl:template>

<xsl:template match="*[not(*)][following-sibling::node()[1][self::text()[normalize-space()]] |
                       preceding-sibling::node()[1][self::text()[normalize-space()]]]" priority="5">
  <x id="{@id}" local-name="{local-name()}">
    <xsl:apply-templates/>
  </x>
</xsl:template>

</xsl:stylesheet>

将您的输入转换为结果

<root>
   <transunit id="002">
      <source>Notice</source>
      <target>Notice</target>
   </transunit>
   <transunit id="003">
      <source>This information U.S.A.</source>
      <target>This information U.S.A.</target>
   </transunit>
   <transunit id="005">
      <source>This product blah blah <x id="006" local-name="companyname">blah bla</x> No other
                warranty expressed or implied. </source>
      <target>This product blah blah <x id="006" local-name="companyname">blah bla</x> No other
                warranty expressed or implied. </target>
   </transunit>
   <transunit id="007">
      <source>This supersedes all previous notices.</source>
      <target>This supersedes all previous notices.</target>
   </transunit>
   <transunit id="009">
      <source>COPYRIGHT LICENSE:</source>
      <target>COPYRIGHT LICENSE:</target>
   </transunit>
   <transunit id="010">
      <source>This information contains <x id="011" local-name="b">in source language</x> , blah blah</source>
      <target>This information contains <x id="011" local-name="b">in source language</x> , blah blah</target>
   </transunit>
</root>

使用Saxon 9.5进行测试。

相关问题