【发布时间】:2014-04-04 14:52:51
【问题描述】:
在 XSLT 2.0 中是否有一个函数可以从 2 个日期计算持续时间?
我正在尝试根据出生日期和当前日期计算以下内容:
- 年龄
- 月龄
【问题讨论】:
在 XSLT 2.0 中是否有一个函数可以从 2 个日期计算持续时间?
我正在尝试根据出生日期和当前日期计算以下内容:
【问题讨论】:
我不知道 XSLT 中有一个预定义的函数来完成这个。但是您始终可以编写自己的代码。下面的解决方案不使用函数,但您可以轻松地将其重写为函数。
计算思路取自here。
还有其他(更短的)方法可以解决此问题,例如,对于特定于 XSLT 2.0 的解决方案,请参见 Mads Hansen 的回答 here。不过,您必须稍微调整您在那里找到的样式表,因为它会输出天数。
输入
<root>
<birth>1964-10-10</birth>
</root>
样式表
<?xml version="1.0"?>
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" />
<xsl:variable name="Birthday" select="//birth[1]"/>
<xsl:variable name="Age">
<xsl:choose>
<xsl:when test="month-from-date(current-date()) > month-from-date($Birthday) or month-from-date(current-date()) = month-from-date($Birthday) and day-from-date(current-date()) >= day-from-date($Birthday)">
<xsl:value-of select="year-from-date(current-date()) - year-from-date($Birthday)" />
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="year-from-date(current-date()) - year-from-date($Birthday) - 1" />
</xsl:otherwise>
</xsl:choose>
</xsl:variable>
<xsl:template match="/root">
<result>
<xsl:value-of select="$Age"/>
</result>
</xsl:template>
</xsl:stylesheet>
输出
<?xml version="1.0" encoding="UTF-8"?><result>49</result>
【讨论】:
注意:这是一个 XSLT 1.0 解决方案;在这里使用 XSLT 2.0 并没有真正的优势(除了方便使用专用函数来提取日期组件 - 无论如何这都是相当微不足道的)。
<xsl:template match="/">
<age-in-months>
<xsl:call-template name="age-in-months">
<xsl:with-param name="date-of-birth" select="'2013-03-03'"/>
<xsl:with-param name="current-date" select="'2014-03-02'"/>
</xsl:call-template>
</age-in-months>
</xsl:template>
<xsl:template name="age-in-months">
<xsl:param name="date-of-birth" />
<xsl:param name="current-date" />
<xsl:param name="y1" select="substring($date-of-birth, 1, 4)"/>
<xsl:param name="y2" select="substring($current-date, 1, 4)"/>
<xsl:param name="m1" select="substring($date-of-birth, 6, 2)"/>
<xsl:param name="m2" select="substring($current-date, 6, 2)"/>
<xsl:param name="d1" select="substring($date-of-birth, 9, 2)"/>
<xsl:param name="d2" select="substring($current-date, 9, 2)"/>
<xsl:value-of select="12 * ($y2 - $y1) + $m2 - $m1 - ($d2 < $d1)"/>
</xsl:template>
</xsl:stylesheet>
请注意,年龄可以通过以下方式获得:
floor($age-in-months div 12)
所以如果你需要,同一个模板可以同时提供。
【讨论】:
在 XSLT 2.0 中是否有一个函数可以从 2 个日期计算持续时间?
是的。除了它是一个运算符,而不是一个函数。只需使用减法运算符“-”。
例如
current-date() - xs:date('1920-03-04')
以天为单位给出我父亲的年龄:
P34332D
由于闰年的复杂性(对于 2 月 29 日出生的人,您如何处理?),以年和月为单位计算他的年龄有点复杂。您可以通过除以 xs:dayTimeDuration('P1D') 将此持续时间减少到天数,然后您可以通过将其除以 365.25 获得总年数的合理近似值,但更准确的计算可能是通过在两个日期上使用 year-from-date() 获得,减去结果,然后如果第一个日期晚于第二个日期,则减去一个 - 这意味着基本上自己编写逻辑。
【讨论】: