3

我想知道这个谓词([1])如何在 muenchian 分组中始终硬编码为 1。经过大量搜索,我并不清楚这个概念。解释为当前节点,与key返回的第一组进行比较。为什么它总是与第一个匹配的键进行比较?另外,我们为什么要contact[count(. | key('contacts-by-surname', surname)[1]) = 1], the =1 part?再次给出 1 是硬编码的。我参考了以下链接

http://www.jenitennison.com/xslt/grouping/muenchian.html

4

3 回答 3

2

假设我们有一个键定义<xsl:key name="contacts-by-surname" match="contact" use="surname"/>,那么表达式key('contacts-by-surname', 'Doe')会为您提供一个节点集,其中包含is的所有contact元素。该表达式为您提供了该“组”中的第一个。surnameDoekey('contacts-by-surname', 'Doe')[1]contact

现在,当使用or处理所有contact元素时,我们通常需要一种方法来识别每个组中的第一个元素。这可以通过或来实现。for-eachapply-templatescontact<xsl:for-each select="contact[count(. | key('contacts-by-surname', surname)[1]) = 1]"><xsl:for-each select="contact[generate-id() = generate-id(key('contacts-by-surname', surname)[1])]">

如果您的要求不同,例如您想识别每个组中的最后一项,那么您当然可以使用不同的谓词,例如<xsl:for-each select="contact[count(. | key('contacts-by-surname', surname)[last()]) = 1]">or <xsl:for-each select="contact[generate-id() = generate-id(key('contacts-by-surname', surname)[last()])]">

于 2011-11-21T13:00:32.287 回答
1

我想知道这个谓词([1])如何在 muenchian 分组中始终硬编码为 1。

这很简单

key()函数为给定组生成所有节点,我们只想从任何组中获取一个节点。

不能保证所有组中都会有两个或更多节点——有些可能只有一个节点。

这就是为什么从每个组中获取第一个(也可能是唯一的)节点是安全和方便的。

我们同样可以从每个组中取出最后一个节点进行分组(但这会降低效率):

<xsl:stylesheet version="1.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>
 <xsl:strip-space elements="*"/>

 <xsl:key name="kNumByMod3" match="num"
  use=". mod 3"/>

 <xsl:template match=
  "num[generate-id()
      =
       generate-id(key('kNumByMod3', . mod 3)[last()])
      ]
  ">


  3k + <xsl:value-of select=". mod 3"/>:
<xsl:text/>
  <xsl:copy-of select="key('kNumByMod3', . mod 3)"/>
 </xsl:template>
 <xsl:template match="text()"/>
</xsl:stylesheet>

应用于此 XML 文档时

<nums>
  <num>01</num>
  <num>02</num>
  <num>03</num>
  <num>04</num>
  <num>05</num>
  <num>06</num>
  <num>07</num>
  <num>08</num>
  <num>09</num>
  <num>10</num>
</nums>

产生想要的、正确分组的结果

  3k + 2:
<num>02</num>
<num>05</num>
<num>08</num>


  3k + 0:
<num>03</num>
<num>06</num>
<num>09</num>


  3k + 1:
<num>01</num>
<num>04</num>
<num>07</num>
<num>10</num>
于 2011-11-21T14:19:34.597 回答
0

基本算法是有两个嵌套循环。外循环从每一组中选择一个代表节点,内循环选择该组中的所有节点(包括被选为代表的节点)。从组中选择一个代表节点的最简单方法是选择第一个,因此选择谓词[1]

于 2011-11-21T15:56:36.790 回答