【问题标题】:XSLT: how to access previous groupXSLT:如何访问上一个组
【发布时间】:2015-07-09 03:29:40
【问题描述】:

我正在为一段代码苦苦挣扎,任何帮助将不胜感激。

简而言之,在我的 XSLT(2.0) 文件中,我有 2 个嵌套循环。 第一个执行基于年份值的分组。 对于这些组中的每一个,内部循环执行一些操作。在这个特定的循环中,在当前组中执行任务时,我需要知道前一组的大小(元素的数量)。 当然,我不知道如何实现这一点。

这是一段 XSLT 代码:

<xsl:for-each-group select=" ... " group-by="year">


        <xsl:for-each select="current-group()">

            <!-- Here I want to know the number of elements of previous group -->

        </xsl:for-each>
 </xsl:for-each-group>

对于第一组,当然 size 需要为 0,因为还没有之前的组。 对于下一组(第二,第三,...),我需要知道前一组的元素数。

例如,如果我们有两个组:

  • 2007 组与元素 data1 data2 data3 data4
  • 2009 年组与元素 data5 data6

当内部循环对“2009 group”执行操作时,我需要知道 2007 group 有 4 个元素。 (数据1数据2数据3数据4)


更多细节!

这是我的 XML 文件的样子。您有一个名为“dblp”的根 racine,您可以在其中找到“proceedings”或“inproceedings”标签。其中每一个都包含对出版物的描述,包括标题、年份、作者/编辑、...。

<dblp>
<proceedings mdate="2007-08-28" key="conf/adma/2007">
    <editor>Reda Alhajj</editor>
    <editor>Hong Gao</editor>
    <editor>Xue Li</editor>
    <editor>Jianzhong Li</editor>
    <editor>Osmar R. Zaïane</editor>
    <title>Advanced Data Mining and Applications, Third International Conference, ADMA 2007, Harbin, China, August 6-8, 2007, Proceedings</title>
    <booktitle>ADMA</booktitle>
    <series href="db/journals/lncs.html">Lecture Notes in Computer Science</series>
    <volume>4632</volume>
    <publisher>Springer</publisher>
    <year>2009</year>
    <isbn>978-3-540-73870-1</isbn>
    <url>db/conf/adma/adma2007.html</url>
</proceedings>
<proceedings mdate="2007-08-28" key="conf/adma/2007">
    <editor>Reda Alhajj</editor>
    <editor>Hong Gao</editor>
    <editor>Xue Li</editor>
    <editor>Jianzhong Li</editor>
    <editor>Osmar R. Zaïane</editor>
    <title>Advanced Data Mining and Applications, Third International Conference, ADMA 2007, Harbin, China, August 6-8, 2007, Proceedings</title>
    <booktitle>ADMA</booktitle>
    <series href="db/journals/lncs.html">Lecture Notes in Computer Science</series>
    <volume>4632</volume>
    <publisher>Springer</publisher>
    <year>1999</year>
    <isbn>978-3-540-73870-1</isbn>
    <url>db/conf/adma/adma2007.html</url>
</proceedings>
<inproceedings mdate="2007-08-28" key="conf/adma/YangLH07">
    <author>Hui Yang</author>
    <author>Reda Alhajj</author>
    <author>Hongyan Liu</author>
    <author>Jun He</author>
    <title>DELAY : A Lazy Approach for Mining Frequent Patterns over High Speed Data Streams.</title>
    <pages>2-14</pages>
    <year>2009</year>
    <crossref>conf/adma/2007</crossref>
    <booktitle>ADMA</booktitle>
    <ee>http://dx.doi.org/10.1007/978-3-540-73871-8_2</ee>
    <url>db/conf/adma/adma2007.html#YangLH07</url>
</inproceedings>
<inproceedings mdate="2007-11-29" key="conf/adma/GuoKG07">
    <author>Yi Guo</author>
    <author>Reda Alhajj</author>
    <author>Paul Wing Hing Kwan</author>
    <author>Junbin Gao</author>
    <title>Learning Optimal Kernel from Distance Metric in Twin Kernel Embedding for Dimensionality Reduction and Visualization of Fingerprints.</title>
    <pages>227-238</pages>
    <year>2007</year>
    <crossref>conf/adma/2007</crossref>
    <booktitle>ADMA</booktitle>
    <ee>http://dx.doi.org/10.1007/978-3-540-73871-8_22</ee>
    <url>db/conf/adma/adma2007.html#GuoKG07</url>
</inproceedings>

这是我之前的 XSLT 代码:

<xsl:for-each-group select="/dblp/*/editor[text() = $currentEditor] | /dblp/*/author[text() = $currentEditor]" group-by="../year">
     <xsl:value-of select="current-grouping-key()"/>
     <xsl:for-each select="current-group()">
         <xsl:variable name="titre" select="(../title)"/>
         <xsl:variable name="linkEE" select="(../ee)"/>
     </xsl:for-each>
</xsl:for-each-group>

“xsl:for-each-group”根据出版物的年份值(进程、进程中)执行分组。如您所见,我选择 特定的编辑或作者。例如,$currentEditor 可以是 'Reda Alhajj'。 对于“Reda Alhajj”,它将创建 3 个组:2009 组(1 个程序 + 1 个程序)、2007 组(1 个程序)和 1999 组(1 个程序) (如您在 XML 文件中所见) 然后,内部循环将遍历每个组的元素以检索更多信息(标题、链接、..)。

我的问题:如何使用新的 xslt 代码实现相同的行为?

<xsl:for-each select="$groups/group">
      how to get current-grouping-key ??
     <xsl:for-each select="*">  title ?? link ??</xsl:for-each>
</xsl:for-each>

非常感谢!


我重新编写了 Martin Hoonen 提供的代码,这是我当前的 XSLT 代码。

<xsl:variable name="groups">
<xsl:for-each-group select="/dblp/*/editor[text() = $currentEditor] | /dblp/*/author[text() = $currentEditor]" group-by="../year">
    <group  year="{../year}">
            <xsl:for-each select="current-group()">
                <elem  titre="{../title}" linkEE="{../ee}" editeurs="{../author | ../editor}">
                </elem>
            </xsl:for-each>
    </group>
</xsl:for-each-group>
</xsl:variable>


<xsl:for-each select="$groups/group">
     <xsl:value-of select="@year"/>

     <xsl:for-each select="elem">
          <xsl:variable name="person" select="@editeurs"/>
          <xsl:for-each select="$person">
               <!-- NOT WORKING TO LOOP SEPARATELY OVER EACH AUTHOR/EDITOR : gives me all author/editors of elem at the first iteration of loop -->
               <xsl:value-of select="."/>
          </xsl:for-each>
     </xsl:for-each>
 </xsl:for-each>

在变量“groups”中,我有一个标签“group”,它对应于一般组(按年份分类)。在这个“组”标签中,我添加了一个与出版物相对应的“elem”标签。实际上,一个组可以由多个出版物组成(例如,在 2009 年,有两个出版物,所以我在这个“组”中有 2 个“elem”,并且我为每个 elem 保存标题,..)。

我的问题是作者/编辑。正如您从 XML 文件中看到的那样,我可以在一个出版物中拥有多个不同的作者或编辑(例如,在我的 XML 文件的第一个程序中,我有 5 个编辑)。 我希望以后能够分别循环遍历它们中的每一个。目前,如您所见,我将它们保存为“elem”的属性,但随后它们被保存为字符串,我无法分别循环遍历它们中的每一个。 有没有人有实现这一目标的想法?

目前 $person 上的循环给了我这个结果: 惠阳 Reda Alhajj Hongyan Liu Jun He

而不是(我可以执行特定处理的分离值):

  • 惠阳
  • Reda Alhajj
  • 刘红艳
  • 何君

任何帮助表示赞赏! :)

【问题讨论】:

  • 你能解释一下你需要什么之前的计数for吗?
  • 如果它显示了预期的输出,您的说明会更加清晰。

标签: xml xslt


【解决方案1】:

您需要将您的组存储到一个根据需要结构化的变量中,例如

<xsl:variable name="groups">
  <xsl:for-each-group select=" ... " group-by="year">
    <group>
      <xsl:copy-of select="current-group()"/>
    </group>
  </xsl:for-each-group>
</xsl:variable>

现在你可以在这里使用

<xsl:for-each select="$groups/group">
  <!-- to compute the size of the previous group -->
  <xsl:variable name="psize" select="count(preceding-sibling::group[1]/*)"/>
  <!-- to iterate over the elements in each group -->
  <xsl:for-each select="*">...</xsl:for-each>
</xsl:for-each>

根据您的编辑,您似乎将editorauthor 元素按父元素的year 分组,然后您想访问其他元素,例如父元素的titleee。如果您知道需要这两个值,则可以更改分组代码以存储它们,例如

<xsl:variable name="groups">
  <xsl:for-each-group select="/dblp/*/editor[. = $currentEditor] | /dblp/*/author[. = $currentEditor]" group-by="../year">
    <group title="{../title}" ee="{../ee}">
      <xsl:copy-of select="current-group()"/>
    </group>
  </xsl:for-each-group>
</xsl:variable>

这将允许您稍后将这些值作为属性访问,例如

<xsl:for-each select="$groups/group">
  <!-- to compute the size of the previous group -->
  <xsl:variable name="psize" select="count(preceding-sibling::group[1]/*)"/>
  <!-- the common, stored values -->
  <xsl:variable name="title" select="@title"/>
  <xsl:variable name="ee" select="@ee"/>
  <!-- to iterate over the elements in each group -->
  <xsl:for-each select="*">...</xsl:for-each>
</xsl:for-each>

【讨论】:

  • 成功了,谢谢。但是,我无法弄清楚如何访问每个“组”的元素。之前,我这样做是为了访问一个组的元素:
  • 成功了,谢谢。但是,我无法弄清楚如何访问每个“组”的元素。之前,在我的内部循环中,我会访问这样的元素(这里是“标题”标签的内容): 我怎样才能在你的内部循环中实现同样的效果: 检索标题 ??
  • 我需要查看输入 XML,路径 ../title 建议您向上导航到父元素,然后访问 title 子元素,因为您没有显示您的 XML,并且没有显示你分组的元素(` ) it is not possible to tell whether the title` 是分组元素或其他元素的一部分。所以编辑你的问题并提供一个示例XML 输入和分组的确切 select 属性。
  • 您好,再次感谢您的帮助!我在第一篇文章中提供了完整的信息,希望你能再次帮助我。 :)
  • @thvdevel,我已经编辑了我的答案,以展示一种在分组到变量时存储数据的方法。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-10-31
  • 2017-10-22
  • 2019-12-20
  • 1970-01-01
  • 2020-11-30
  • 2018-06-27
  • 1970-01-01
相关资源
最近更新 更多