XSL 如何找到特定日期的儒略日?
XSL how to find the Julian day for a specific date?
我有这个简单的 XML-文件
<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" href="faan.xsl"?>
<datum>2016-05-17</datum>
我想使用 XSL(XSL 2.0 和扩展不是一个选项)来计算这个日期的儒略日(正确答案是 2457526,这只是练习!)并想出了这种风格 sheet这似乎在许多地方都是复制粘贴的。
但是,当在资源管理器中打开文件时,它只会给我日期 2016-05-17,当我在 Excel 中打开它时,它说我不能在这个地方使用 xsl:with-param。
我显然错过了一些非常简单的东西,但是什么?
<?xml version="1.0"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" indent="yes"/>
<xsl:template match="/">
<xsl:for-each select="datum">
<xsl:sort select="datum"/>
<dateline>
<datum><xsl:value-of select="datum"/></datum>
</dateline>
</xsl:for-each>
</xsl:template>
<xsl:template match="datum">
<xsl:call-template name="calculate-julian-day" />
<xsl:with-param name="year" select="substring(datum,1,4)" />
<xsl:with-param name="month" select="substring(datum,6,2)" />
<xsl:with-param name="day" select="substring(datum,9,2)" />
</xsl:template>
<xsl:template name="calculate-julian-day">
<xsl:param name="year"/>
<xsl:param name="month"/>
<xsl:param name="day"/>
<xsl:variable name="a" select="floor((14 - $month) div 12)"/>
<xsl:variable name="y" select="$year + 4800 - $a"/>
<xsl:variable name="m" select="$month + 12 * $a - 3"/>
<xsl:value-of select="$day + floor((153 * $m + 2) div 5) + $y * 365 + floor($y div 4) - floor ($y div 100) + floor($y div 400) - 32045"/>
</xsl:template>
</xsl:stylesheet>
这是一种可能的解决方案:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:template match="datum">
<xsl:call-template name="date-to-julian-day">
<xsl:with-param name="date" select="."/>
</xsl:call-template>
</xsl:template>
<!--
==========================================================================
Template: date-to-julian-day
Description: Convert a date to julian day
Parameters:-
<year> <month> <day>
or
<date> (format: yyyymmdd or yyyy-mm-dd)
========================================================================== -->
<xsl:template name="date-to-julian-day">
<xsl:param name="year"/>
<xsl:param name="month"/>
<xsl:param name="day"/>
<!-- or -->
<xsl:param name="date" select="''"/>
<!-- trim down date -->
<xsl:variable name="tdate" select="translate($date,'-','')"/>
<!-- decide which params were passed -->
<xsl:variable name="yyyy">
<xsl:choose>
<xsl:when test="string-length($date) > 0">
<xsl:value-of select="substring($tdate,1,4)"/>
</xsl:when>
<xsl:otherwise><xsl:value-of select="$year"/></xsl:otherwise>
</xsl:choose>
</xsl:variable>
<xsl:variable name="mm">
<xsl:choose>
<xsl:when test="string-length($date) > 0">
<xsl:value-of select="substring($tdate,5,2)"/>
</xsl:when>
<xsl:otherwise><xsl:value-of select="$month"/></xsl:otherwise>
</xsl:choose>
</xsl:variable>
<xsl:variable name="dd">
<xsl:choose>
<xsl:when test="string-length($date) > 0">
<xsl:value-of select="substring($tdate,7,2)"/>
</xsl:when>
<xsl:otherwise><xsl:value-of select="$day"/></xsl:otherwise>
</xsl:choose>
</xsl:variable>
<!-- pre-calcs -->
<xsl:variable name="j0" select="ceiling(($mm - 14) div 12)"/>
<xsl:variable name="j1" select="floor((1461 * ($yyyy + 4800 + $j0)) div 4)"/>
<xsl:variable name="j2" select="floor((367 * ($mm - 2 - (12 * $j0))) div 12)"/>
<xsl:variable name="j3"
select="floor((3 * floor(($yyyy + 4900 + $j0) div 100)) div 4)"/>
<!-- final calc -->
<xsl:value-of select="$j1 + $j2 - $j3 + $dd - 32075"/>
</xsl:template>
</xsl:stylesheet>
当此转换应用于提供的 XML 文档时:
<datum>2016-05-17</datum>
产生了想要的、正确的结果:
2457526
归因:
所提供的代码是 datetime_lib.xsl
XSLT 1.0 日期时间算术和转换模板库的一部分,由我的朋友 Martin Rowlinson(XSelerator 的作者)编写,是有史以来最好的 XSLT IDE,依然是易用性强的光辉典范UI。
有时在 2010 年左右,XSelerator 在 sourceforge.net 上免费提供,这就是人们通常获取这些有价值的模板库的方式..
我有这个简单的 XML-文件
<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" href="faan.xsl"?>
<datum>2016-05-17</datum>
我想使用 XSL(XSL 2.0 和扩展不是一个选项)来计算这个日期的儒略日(正确答案是 2457526,这只是练习!)并想出了这种风格 sheet这似乎在许多地方都是复制粘贴的。 但是,当在资源管理器中打开文件时,它只会给我日期 2016-05-17,当我在 Excel 中打开它时,它说我不能在这个地方使用 xsl:with-param。 我显然错过了一些非常简单的东西,但是什么?
<?xml version="1.0"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" indent="yes"/>
<xsl:template match="/">
<xsl:for-each select="datum">
<xsl:sort select="datum"/>
<dateline>
<datum><xsl:value-of select="datum"/></datum>
</dateline>
</xsl:for-each>
</xsl:template>
<xsl:template match="datum">
<xsl:call-template name="calculate-julian-day" />
<xsl:with-param name="year" select="substring(datum,1,4)" />
<xsl:with-param name="month" select="substring(datum,6,2)" />
<xsl:with-param name="day" select="substring(datum,9,2)" />
</xsl:template>
<xsl:template name="calculate-julian-day">
<xsl:param name="year"/>
<xsl:param name="month"/>
<xsl:param name="day"/>
<xsl:variable name="a" select="floor((14 - $month) div 12)"/>
<xsl:variable name="y" select="$year + 4800 - $a"/>
<xsl:variable name="m" select="$month + 12 * $a - 3"/>
<xsl:value-of select="$day + floor((153 * $m + 2) div 5) + $y * 365 + floor($y div 4) - floor ($y div 100) + floor($y div 400) - 32045"/>
</xsl:template>
</xsl:stylesheet>
这是一种可能的解决方案:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:template match="datum">
<xsl:call-template name="date-to-julian-day">
<xsl:with-param name="date" select="."/>
</xsl:call-template>
</xsl:template>
<!--
==========================================================================
Template: date-to-julian-day
Description: Convert a date to julian day
Parameters:-
<year> <month> <day>
or
<date> (format: yyyymmdd or yyyy-mm-dd)
========================================================================== -->
<xsl:template name="date-to-julian-day">
<xsl:param name="year"/>
<xsl:param name="month"/>
<xsl:param name="day"/>
<!-- or -->
<xsl:param name="date" select="''"/>
<!-- trim down date -->
<xsl:variable name="tdate" select="translate($date,'-','')"/>
<!-- decide which params were passed -->
<xsl:variable name="yyyy">
<xsl:choose>
<xsl:when test="string-length($date) > 0">
<xsl:value-of select="substring($tdate,1,4)"/>
</xsl:when>
<xsl:otherwise><xsl:value-of select="$year"/></xsl:otherwise>
</xsl:choose>
</xsl:variable>
<xsl:variable name="mm">
<xsl:choose>
<xsl:when test="string-length($date) > 0">
<xsl:value-of select="substring($tdate,5,2)"/>
</xsl:when>
<xsl:otherwise><xsl:value-of select="$month"/></xsl:otherwise>
</xsl:choose>
</xsl:variable>
<xsl:variable name="dd">
<xsl:choose>
<xsl:when test="string-length($date) > 0">
<xsl:value-of select="substring($tdate,7,2)"/>
</xsl:when>
<xsl:otherwise><xsl:value-of select="$day"/></xsl:otherwise>
</xsl:choose>
</xsl:variable>
<!-- pre-calcs -->
<xsl:variable name="j0" select="ceiling(($mm - 14) div 12)"/>
<xsl:variable name="j1" select="floor((1461 * ($yyyy + 4800 + $j0)) div 4)"/>
<xsl:variable name="j2" select="floor((367 * ($mm - 2 - (12 * $j0))) div 12)"/>
<xsl:variable name="j3"
select="floor((3 * floor(($yyyy + 4900 + $j0) div 100)) div 4)"/>
<!-- final calc -->
<xsl:value-of select="$j1 + $j2 - $j3 + $dd - 32075"/>
</xsl:template>
</xsl:stylesheet>
当此转换应用于提供的 XML 文档时:
<datum>2016-05-17</datum>
产生了想要的、正确的结果:
2457526
归因:
所提供的代码是 datetime_lib.xsl
XSLT 1.0 日期时间算术和转换模板库的一部分,由我的朋友 Martin Rowlinson(XSelerator 的作者)编写,是有史以来最好的 XSLT IDE,依然是易用性强的光辉典范UI。
有时在 2010 年左右,XSelerator 在 sourceforge.net 上免费提供,这就是人们通常获取这些有价值的模板库的方式..