我有一个"用户"与其他"用户"的亲子关系。用户"父母"是approverID。我需要对这个列表进行排序,以便列表中的父项之前没有子项,可以使用XSLT 2.0。输入xml示例:
<userList>
<user>
<userID>4</userID>
<approverID>2</approverID>
</user>
<user>
<userID>5</userID>
<approverID>2</approverID>
</user>
<user>
<userID>3</userID>
<approverID>1</approverID>
</user>
<user>
<userID>2</userID>
<approverID>1</approverID>
</user>
<user>
<userID>1</userID>
<approverID>10</approverID>
</user>
<user>
<userID>6</userID>
<approverID>7</approverID>
</user>
<user>
<userID>7</userID>
<approverID>10</approverID>
</user>
</userList>
会有一个父子结构(不确定表明它的最佳方式)
1 {2 {4,5},3}
7 {6}
输出XML看起来像
<userList>
<user>
<userID>1</userID>
<approverID>10</userID>
</user>
<user>
<userID>2</userID>
<approverID>1</approverID>
</user>
<user>
<userID>3</userID>
<approverID>1</approverID>
</user>
<user>
<userID>4</userID>
<approverID>2</approverID>
</user>
<user>
<userID>5</userID>
<approverID>2</approverID>
</user>
<user>
<userID>7</userID>
<approverID>10</approverID>
</user>
<user>
<userID>6</userID>
<approverID>7</approverID>
</user>
</userList>
唯一的要求是,子用户永远不会在父级之前,但除此之外,无论如何都可以对其进行排序。我觉得我可以递归地做到这一点,但我知道这不是像XSLT这样的函数式编程语言的最佳选择。
答案 0 :(得分:1)
您的输入和输出之间似乎存在一些不一致(我认为您的输出在两个地方违反了您的要求),但我认为这就是您的目标:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" indent="yes" omit-xml-declaration="yes" />
<xsl:key name="kUserByApprover" match="user" use="approverID"/>
<xsl:key name="kUserById" match="user" use="userID"/>
<xsl:template match="@* | node()" name="copy">
<xsl:copy>
<xsl:apply-templates select="@* | node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="userList">
<xsl:copy>
<!-- Process users whose approver is not present -->
<xsl:apply-templates select="user[not(key('kUserById', approverID))]" />
</xsl:copy>
</xsl:template>
<xsl:template match="user">
<xsl:call-template name="copy" />
<!-- Process child users -->
<xsl:apply-templates select="key('kUserByApprover', userID)" />
</xsl:template>
</xsl:stylesheet>
在样本输入上运行时,结果为:
<userList>
<user>
<userID>1</userID>
<approverID>10</approverID>
</user>
<user>
<userID>3</userID>
<approverID>1</approverID>
</user>
<user>
<userID>2</userID>
<approverID>1</approverID>
</user>
<user>
<userID>4</userID>
<approverID>2</approverID>
</user>
<user>
<userID>5</userID>
<approverID>2</approverID>
</user>
<user>
<userID>7</userID>
<approverID>10</approverID>
</user>
<user>
<userID>6</userID>
<approverID>7</approverID>
</user>
</userList>