【问题标题】:How to Sort Dates in XSL?如何在 XSL 中对日期进行排序?
【发布时间】:2016-04-16 08:50:16
【问题描述】:

我有一个下面的 XML 结构,我想对日期进行排序并将一个日期节点更新为最新日期。日期采用 YYYY/mm/dd 格式。下面是 XML 结构。

更具体地说,我在下面举一个例子。 假设有 3 个保险生效日期 2015/01/01、2015/01/02、2015/01/03,那么 customerEffectiveDate 应更新为 2015/01/03。

关于 XML 结构的注意事项: 1. 产品数量可以从 1 到 10。 2.覆盖节点可以从1到Many。

<Map>
    <customer>
        <customerDetails>
            <!-- The customerEffectiveDate below should be updated to the latest among all the effectiveDate fron coverage.-->
            <customerEffectiveDate>2014/06/02</customerEffectiveDate>
        </customerDetails>
    </customer>
    <products>
        <product1>
            <!-- Coverage Nodes can occur multiple times. There is no limit.-->
            <coverage>
                <effectiveDate>2015/12/01</effectiveDate>
            </coverage>
            <coverage>
                <effectiveDate>2015/11/01</effectiveDate>
            </coverage>
        </product1>
        <product2>
            <coverage>
                <effectiveDate>2014/12/01</effectiveDate>
            </coverage>
            <coverage>
                <effectiveDate>2015/09/01</effectiveDate>
            </coverage>
        </product2>
        .
        .
        .
        .
        .
        .
        .
        .

        <product10></product10>
    </products>
</Map>

另外一点需要注意的是我使用的是 XSL 1.0。有人可以帮忙吗?

我已经看过thisthisthis

谢谢。

【问题讨论】:

    标签: xml xslt xslt-1.0


    【解决方案1】:

    鉴于该格式,您可以轻松对其进行排序,编写一个模板

    <xsl:template match="customer/customerDetails/customerEffectiveDate">
      <xsl:copy>
        <xsl:for-each select="//coverage/effectiveDate">
          <xsl:sort select="." data-type="text" order="descending"/>
          <xsl:if test="position() = 1">
            <xsl:value-of select="."/>
          </xsl:if>
       </xsl:for-each>
     </xsl:copy>
    </xsl:template>
    

    加上身份转换模板

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

    复制其余部分不变。

    【讨论】:

    • 条件 会做什么?而什么是“身份转换模板”?
    • 我已经编辑了代码以显示身份转换模板的外观。至于校验,嗯,代码按降序排序,然后取第一个值,最新日期,然后输出。
    【解决方案2】:

    这可能不是最简单的方法,但是这种方法对&lt;product1-10&gt;标签下的所有&lt;coverage&gt;标签进行排序,从所有&lt;effectiveDate&gt;值中提取最新值并复制其余值。

    <?xml version="1.0" encoding="UTF-8"?>
    <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
      <xsl:output method="xml" indent="yes"/>
    
    <xsl:template match="node()|@*">
      <xsl:copy>
        <xsl:apply-templates select="node()|@*"/>
      </xsl:copy>
    </xsl:template>
    
    <!-- Process <products> tag with higher priority, so that the follwing template does not match -->
    <xsl:template match="products" priority="1">
      <xsl:copy>
        <xsl:apply-templates select="node()|@*"/>
      </xsl:copy>
    </xsl:template>
    
    <xsl:template match="*[starts-with(local-name(),'product')]">
      <xsl:element name="{name()}">
        <xsl:for-each select="coverage">
          <xsl:sort select="effectiveDate/text()" order="descending" />
          <xsl:copy-of select="." />
        </xsl:for-each>
      </xsl:element>
    </xsl:template>
    
    <!-- extract the first 'effectiveDate' after sorting all values -->
    <xsl:template match="customerEffectiveDate">
      <xsl:variable name="latest">
        <xsl:for-each select="../../../products//effectiveDate">
          <xsl:sort select="text()" order="descending" />
          <xsl:if test="position() = 1">
            <xsl:value-of select="." />
          </xsl:if>
        </xsl:for-each>
      </xsl:variable>
      <customerEffectiveDate><xsl:copy-of select="$latest" /></customerEffectiveDate>
    </xsl:template>
    
    </xsl:stylesheet>
    

    【讨论】:

      猜你喜欢
      • 2019-09-21
      • 1970-01-01
      • 1970-01-01
      • 2021-12-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-06-28
      • 1970-01-01
      相关资源
      最近更新 更多