我有一个可怕的
XML,我需要通过BizTalk进行处理,我已设法将其规范化为下面的示例.我不是XSLT忍者,但在网络和VS2010调试器之间,我可以找到我的方式围绕XSL.
我现在需要一个聪明的XSLT来“清除”重复的元素,只保留最新的元素,由ValidFromDate属性中的日期决定.
ValidFromDate属性属于XSD:Date类型.
<SomeData> <A ValidFromDate="2011-12-01">A_1</A> <A ValidFromDate="2012-01-19">A_2</A> <B CalidFromDate="2011-12-03">B_1</B> <B ValidFromDate="2012-01-17">B_2</B> <B ValidFromDate="2012-01-19">B_3</B> <C ValidFromDate="2012-01-20">C_1</C> <C ValidFromDate="2011-01-20">C_2</C> </SomeData>
转型后,我只想保留这些线:
<SomeData> <A ValidFromDate="2012-01-19">A_2</A> <B ValidFromDate="2012-01-19">B_3</B> <C ValidFromDate="2012-01-20">C_1</C> </SomeData>
关于如何将XSL放在一起的任何线索?我已经清空互联网试图找到一个解决方案,我已经尝试了很多聪明的XSL排序脚本,但没有一个我觉得把我带到了正确的方向.
比@lwburk更简单,更简单的XSLT 1.0解决方案:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output omit-xml-declaration="yes" indent="yes"/> <xsl:key name="kName" match="*/*" use="name()"/> <xsl:template match="/"> <xsl:apply-templates select= "*/*[generate-id() = generate-id(key('kName',name())[1]) ] "/> </xsl:template> <xsl:template match="*/*"> <xsl:for-each select="key('kName',name())"> <xsl:sort select="@ValidFromDate" order="descending"/> <xsl:if test="position() = 1"> <xsl:copy-of select="."/> </xsl:if> </xsl:for-each> </xsl:template> </xsl:stylesheet>
当此转换应用于提供的XML文档时:
<SomeData> <A ValidFromDate="2011-12-01">A_1</A> <A ValidFromDate="2012-01-19">A_2</A> <B CalidFromDate="2011-12-03">B_1</B> <B ValidFromDate="2012-01-17">B_2</B> <B ValidFromDate="2012-01-19">B_3</B> <C ValidFromDate="2012-01-20">C_1</C> <C ValidFromDate="2011-01-20">C_2</C> </SomeData>
产生了想要的正确结果:
<A ValidFromDate="2012-01-19">A_2</A> <B ValidFromDate="2012-01-19">B_3</B> <C ValidFromDate="2012-01-20">C_1</C>