XQuery/分组项
外观
< XQuery
您在一组数据中拥有许多与类别关联的项目。您想要创建一个按类别对项目进行排序的报表。
我们将分三个步骤执行查询。
- 使用 FLWOR 语句,使用 distinct-values() 函数创建不同类别的序列。
- 对于类别序列中的每个项目,选择属于该类别的所有项目。这可以通过在 XPath 选择器末尾添加谓词(where 子句)来完成。它的形式为 data/item[x=y],如果 x=y 返回 true,则该项目将被添加到序列中。
- 对于 FLWOR 语句中的每个结果集,返回类别名称,然后返回该类别中的所有项目。
<items>
<item>
<name>item #1</name>
<category>red</category>
</item>
<item>
<name>item #1</name>
<category>red</category>
</item>
<item>
<name>item #2</name>
<category>green</category>
</item>
<item>
<name>item #3</name>
<category>red</category>
</item>
<item>
<name>item #4</name>
<category>blue</category>
</item>
<item>
<name>item #5</name>
<category>red</category>
</item>
<item>
<name>item #6</name>
<category>blue</category>
</item>
<item>
<name>item #7</name>
<category>green</category>
</item>
<item>
<name>item #8</name>
<category>red</category>
</item>
</items>
以下 XQuery 将演示此技术。请注意,所有类别的不同值存储在 $distinct-categories 变量中。
xquery version "1.0";
declare option exist:serialize "method=xhtml media-type=text/html";
(: load the items :)
let $data := doc('/db/mdr/apps/training/labs/04-group-by/data.xml')/items
let $distinct-categories := distinct-values($data/item/category/text())
return
<html>
<body>
<table border="1">
<thead>
<tr>
<th>Category</th>
<th>Items</th>
</tr>
</thead>
<tbody>
{
for $category in $distinct-categories
return
<tr>
<td>{$category}</td>
<td>{string-join($data/item[category=$category]/name/text(), ', ')}</td>
</tr>
}
</tbody>
</table>
</body>
</html>
在上面的查询中,语句
$data/item[category=$category]
表示“从数据集中获取所有类别元素等于当前类别的项目。”
string-join() 函数只是在输出流中的项目之间放置一个逗号和一个空格字符串,以便于阅读。
类别 | 项目 |
---|---|
红色 | 项目 #1,项目 #3,项目 #5,项目 #8 |
绿色 | 项目 #2,项目 #7 |
蓝色 | 项目 #4,项目 #6 |
请注意,您不受限于将项目置于单个类别中。将多个类别添加到项目中不需要对脚本进行任何更改。
您也可以随时将新类别添加到此列表中,而无需更改上面的程序。只要类别元素存在范围索引,所有类别的列表就会很快创建,即使对于数百万条记录也是如此。