【问题标题】:Transform all child siblings into parent-like node将所有子兄弟节点转换为类父节点
【发布时间】:2021-11-18 01:17:29
【问题描述】:

需要将所有子元素转换为父级节点,方法是使它们具有相同的层次结构级别和名称。生成的新元素必须包含子元素的所有属性并保留父元素的属性。

源 XML

<?xml version="1.0" encoding="UTF-8"?>
<entry>

  <line id="001" att1="aaa" att2="bbb" att3="ccc"/>
  <line id="002" att1="ddd" att2="eee" att3="fff"/>
  <line id="003" att1="ggg" att2="hhh" att3="iii">

    <subline  x="name" z="lastname"/>
    <subline  x="name2" z="lastname2"/>
    <underline  a="bar" b="foo"/>
  </line>

</entry>

期望的输出

<entry>

  <line id="001" att1="aaa" att2="bbb" att3="ccc"/> <!-- with or without empty x and z attributes' values-->
  <line id="002" att1="ddd" att2="eee" att3="fff"/> <!-- with or without empty x and z values-->
  <line id="003" att1="ggg" att2="hhh" att3="iii" x="name" z="lastname"/>
  <line id="003" att1="ggg" att2="hhh" att3="iii" x="name2" z="lastname2"/>
  <line id="003" att1="ggg" att2="hhh" att3="iii" a="bar" b="foo"/>

</entry>

提供 XSLT 代码

当前代码只匹配第一个子元素。 我想改变所有其他人

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:msxsl="urn:schemas-microsoft-com:xslt" exclude-result-prefixes="msxsl">
  <xsl:output method="xml" indent="yes"/>



  <xsl:template match="line">
    <line>
      <xsl:copy-of select="@*"/>
      <xsl:attribute name="x">
        <xsl:value-of select="subline/@x"/>
      </xsl:attribute>

      <xsl:attribute name="z">
        <xsl:value-of select="subline/@z"/>
      </xsl:attribute>

      <xsl:apply-templates select="node()"/>
    </line>
  </xsl:template>
  
  
    <!-- ===== delete child elements ====== -->
  <xsl:template match="subline"/>
  <xsl:template match="underline"/>


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


</xsl:stylesheet>

补充说明(可能有用):所有属性名称都是预先知道的

【问题讨论】:

    标签: xml xslt xslt-1.0


    【解决方案1】:

    我建议这样处理:

    <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
      version="1.0">
    
      <xsl:template match="@* | node()">
        <xsl:copy>
          <xsl:apply-templates select="@* | node()"/>
        </xsl:copy>
      </xsl:template>
      
      <xsl:template match="line[*]">
        <xsl:apply-templates/>
      </xsl:template>
      
      <xsl:template match="line/*">
        <line>
          <xsl:copy-of select="../@* | @*"/>
        </line>
      </xsl:template>
    
    </xsl:stylesheet>
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多