在xslt中将短格式的星期转换为日期名称
我有一些简短的日名,如:在xslt中将短格式的星期转换为日期名称,xslt,Xslt,我有一些简短的日名,如: M -> Monday T -> Tuesday W -> Wednesday R -> Thursday F -> Friday S -> Saturday U -> Sunday 如何使用xslt将MRF之类的xml元素转换为长版本星期一、星期四、星期五 根据评论更新 日子不会再重复了 应该可以了。。。也许还有更优雅的解决方案- <xsl:stylesheet version="1.0" xmlns:xsl="htt
M -> Monday
T -> Tuesday
W -> Wednesday
R -> Thursday
F -> Friday
S -> Saturday
U -> Sunday
如何使用xslt将MRF之类的xml元素转换为长版本星期一、星期四、星期五
根据评论更新
日子不会再重复了
应该可以了。。。也许还有更优雅的解决方案-
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="/days">
<long-days>
<xsl:if test="contains(.,'M')">Monday<xsl:if test="string-length(substring-before(.,'M'))=string-length(.)-1">,</xsl:if></xsl:if>
<xsl:if test="contains(.,'T')">Tuesday<xsl:if test="string-length(substring-before(.,'T'))=string-length(.)-1">,</xsl:if></xsl:if>
<xsl:if test="contains(.,'W')">Wednesday<xsl:if test="string-length(substring-before(.,'W'))=string-length(.)-1">,</xsl:if></xsl:if>
<xsl:if test="contains(.,'R')">Thursday<xsl:if test="string-length(substring-before(.,'R'))=string-length(.)-1">,</xsl:if></xsl:if>
<xsl:if test="contains(.,'F')">Friday<xsl:if test="string-length(substring-before(.,'F'))=string-length(.)-1">,</xsl:if></xsl:if>
<xsl:if test="contains(.,'S')">Saturday<xsl:if test="string-length(substring-before(.,'S'))=string-length(.)-1">,</xsl:if></xsl:if>
<xsl:if test="contains(.,'U')">Sunday<xsl:if test="string-length(substring-before(.,'U'))=string-length(.)-1">,</xsl:if></xsl:if>
</long-days>
</xsl:template>
此样式表
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:d="day"
exclude-result-prefixes="d">
<d:d l="M" n="Monday"/>
<d:d l="T" n="Tuesday"/>
<d:d l="W" n="Wednesday"/>
<d:d l="R" n="Thursday"/>
<d:d l="F" n="Friday"/>
<d:d l="S" n="Saturday"/>
<d:d l="U" n="Sunday"/>
<xsl:variable name="vDays" select="document('')/*/d:d"/>
<xsl:template match="days">
<long-days>
<xsl:apply-templates
select="$vDays[contains(current(),@l)]"/>
</long-days>
</xsl:template>
<xsl:template match="d:d">
<xsl:value-of select="@n"/>
<xsl:if test="position()!=last()">,</xsl:if>
</xsl:template>
</xsl:stylesheet>
通过此输入:
<days>MRF</days>
输出:
<long-days>Monday,Thursday,Friday</long-days>
编辑:对于漫游者,保留顺序:
<xsl:variable name="vCurrent" select="current()"/>
<xsl:apply-templates
select="$vDays[contains($vCurrent,@l)]">
<xsl:sort select="substring-before($vCurrent,@l)"/>
</xsl:apply-templates>
注意:由于天数不会重复,这与使用空字符串分隔符按顺序查找项目存在的情况相同。当前接受的解决方案始终按时间顺序显示长天数名称,此外,它不会显示重复代码天数 假设我们有以下XML文档: I.此XSLT 1.0转换: 应用于上述文档时,会产生所需的正确结果: 二,。此XSLT 2.0转换: 应用于同一XML文档时: 产生所需的正确结果:
你能把你的答案扩大到包括我在原始问题中给出的例子吗?或者我只需要包括一周中的所有日子?添加逗号可以吗?很接近,因为USM的逗号在周一、周六、周日放错了位置,我必须看看是否保证了天数的顺序为什么不无条件添加逗号,将结果放入变量中,然后去掉最后一个不需要的逗号?@StevenWilkins:天可以重复吗?@Alejandro-天不会重复。您需要告诉我们这是XSLT 1.0还是2.0。这方面的问题在2.0中总是比较容易。好问题,+1。请参阅我的答案,了解一个解决方案,该解决方案没有Kay@Michael-Kay博士提到的@Alejandro解决方案的缺点。还添加了一个XSLT 2.0解决方案:美好的我喜欢你定义一种关联数组l,n的方式。这就是这么做的好处。您会看到比您自己的解决方案更好的解决方案。我真的不喜欢依赖文档的解决方案。如果您使用的是XSLT2.0,那么可以将查找表放入适当的全局变量中。使用1.0,在大多数情况下,将查找表作为单独的XML文档更为有效。此外,除非数据量非常小,否则查找表应该使用键。解决方案似乎假设输入中字母的顺序无关紧要,这不是要求的一部分。@Michael Kay:答案不取决于文档。它只有内联结构XML数据,可以适当地适应用例外部源XSLT2.0变量。答案是使用第二个数据源来驱动转换,这是一种比条件指令更好的模式。@Michael Kay:您在输入中写的字母顺序无关紧要,这不是要求的一部分,也不是要求的一部分。
<days>STMSU</days>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:my="my:my" exclude-result-prefixes="my" >
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<my:days>
<M>Monday</M>
<T>Tuesday</T>
<W>Wednesday</W>
<R>Thursday</R>
<F>Friday</F>
<S>Saturday</S>
<U>Sunday</U>
</my:days>
<xsl:key name="kLongByShort" match="my:days/*"
use="name()"/>
<xsl:variable name="vstylesheet"
select="document('')"/>
<xsl:template match="days">
<long-days>
<xsl:call-template name="expand"/>
</long-days>
</xsl:template>
<xsl:template name="expand">
<xsl:param name="pcodeString" select="."/>
<xsl:if test="$pcodeString">
<xsl:variable name="vchar" select=
"substring($pcodeString,1,1)"/>
<xsl:for-each select="$vstylesheet">
<xsl:value-of select=
"concat(key('kLongByShort',$vchar),
substring(',',1,string-length($pcodeString)-1)
)
"/>
</xsl:for-each>
<xsl:call-template name="expand">
<xsl:with-param name="pcodeString" select=
"substring($pcodeString,2)"/>
</xsl:call-template>
</xsl:if>
</xsl:template>
</xsl:stylesheet>
<long-days>Saturday,Tuesday,Monday,Saturday,Sunday</long-days>
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
exclude-result-prefixes="xs">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:variable name="vshortCodes" as="xs:integer+"
select="string-to-codepoints('MTWRFSU')"/>
<xsl:variable name="vlongDays" as="xs:string+"
select="'Monday','Tuesday','Wenesday','Thursday',
'Friday','Saturday','Sunday'
"/>
<xsl:template match="days">
<long-days>
<xsl:for-each select="string-to-codepoints(.)">
<xsl:value-of separator="" select=
"for $pos in position() ne last()
return
($vlongDays[index-of($vshortCodes,current())],
','[$pos])
"/>
</xsl:for-each>
</long-days>
</xsl:template>
</xsl:stylesheet>
<days>STMSU</days>
<long-days>Saturday,Tuesday,Monday,Saturday,Sunday</long-days>