【问题标题】:make xml element unique using xslt-3使用 xslt-3 使 xml 元素唯一
【发布时间】:2018-08-03 12:19:00
【问题描述】:

鉴于以下示例 xml,我如何使 RECORD ID 元素和 TITLEID 具有唯一值,从值 1 开始,然后继续?

<CATALOG>
   <CD>
    <RECORD ID="109">
       <TITLEID>54</TITLEID>
       <ARTIST>Bob Dylan</ARTIST>
       <COUNTRY>USA</COUNTRY>
       <COMPANY>Columbia</COMPANY>
       <PRICE>10.90</PRICE>
       <YEAR>1985</YEAR> </CD>
    </RECORD>
   <CD>
     <RECORD ID="187">
       <TITLEID>88</TITLEID>
       <ARTIST>Bonnie Tyler</ARTIST>
       <COUNTRY>UK</COUNTRY>
       <COMPANY>CBS Records</COMPANY>
       <PRICE>9.90</PRICE>
       <YEAR>1988</YEAR> </CD>
     </RECORD>
</CATALOG>

预期结果:

  <CATALOG>
       <CD>
        <RECORD ID="1">
           <TITLEID>1</TITLEID>
           <ARTIST>Bob Dylan</ARTIST>
           <COUNTRY>USA</COUNTRY>
           <COMPANY>Columbia</COMPANY>
           <PRICE>10.90</PRICE>
           <YEAR>1985</YEAR> </CD>
        </RECORD>
       <CD>
         <RECORD ID="2">
           <TITLEID>2</TITLEID>
           <ARTIST>Bonnie Tyler</ARTIST>
           <COUNTRY>UK</COUNTRY>
           <COMPANY>CBS Records</COMPANY>
           <PRICE>9.90</PRICE>
           <YEAR>1988</YEAR> </CD>
         </RECORD>
    </CATALOG>

我尝试使用 xs:unique 属性,但我没有设法让它正常工作

【问题讨论】:

  • 请向我们展示一个格式良好的 XML 输入样本和结果样本,其中有一个开头的 CD 标记和一个开头的 RECORD 标记,首先用 CD 关闭,然后用 RECORD 关闭格式不正确。请求 XSLT 帮助但将架构元素 xs:unique 作为“尝试”听起来很奇怪,如果您倾向于纯 XSLT 3 方法,请查看任何 XSLT 版本中的 xsl:numberxsl:accumulator

标签: xslt-3.0


【解决方案1】:

使用累加器 (https://www.w3.org/TR/xslt-30/#element-accumulator) 的 XSLT 3 解决方案位于 https://xsltfiddle.liberty-development.net/6qVRKwn/0 并且确实

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

  <xsl:mode on-no-match="shallow-copy" use-accumulators="cd-count"/>

  <xsl:accumulator name="cd-count" as="xs:integer" initial-value="0">
      <xsl:accumulator-rule match="CD" select="$value + 1"/>
  </xsl:accumulator>

  <xsl:template match="RECORD/@ID">
      <xsl:attribute name="{name()}" select="..!accumulator-before('cd-count')"/>
  </xsl:template>

  <xsl:template match="RECORD/TITLEID">
      <xsl:copy>
          <xsl:value-of select="accumulator-before('cd-count')"/>
      </xsl:copy>
  </xsl:template>

</xsl:stylesheet>

经典的解决方案是使用xsl:number (https://www.w3.org/TR/xslt-30/#element-number),如https://xsltfiddle.liberty-development.net/6qVRKwn/1

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

  <xsl:mode on-no-match="shallow-copy"/>

  <xsl:template match="RECORD/@ID">
      <xsl:attribute name="{name()}">
          <xsl:number count="CD"/>
      </xsl:attribute>
  </xsl:template>

  <xsl:template match="RECORD/TITLEID">
      <xsl:copy>
          <xsl:number count="CD"/>
      </xsl:copy>
  </xsl:template>

</xsl:stylesheet>

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-09-29
    • 2018-01-19
    • 2014-05-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多