如何限制 XQuery 结果中的 return 顺序?

How to restrict return order in XQuery results?

这是新手问题。我最近才开始学习 XQuery 和 XPath。

考虑这个XML

<employees>
    <employee empid="1">
        <ename>KING</ename>
        <mgr></mgr>
        <hiredate>17-11-1981</hiredate>
    </employee>
    <employee empid="2">
        <ename>BLAKE</ename>
        <mgr>7839</mgr>
        <hiredate>1-5-1981</hiredate>
        <test>
            <sub1>one</sub1>
            <sub2>two</sub2>
        </test>
    </employee>
</employees>

当我执行以下 XQuery 时,

let $db := db:open("example", "documents/employee.xml")
for $item in $db/(/employees/employee,/employees/employee/test)
let $empid := $item/@empid
let $ename := $item/ename
let $sub1 := $item/sub1
let $hiredate := $item/hiredate
let $sub2 := $item/sub2
return ($empid,$ename,$sub1,$hiredate,$sub2)

我得到了...

empid="1"
<ename>KING</ename>
<hiredate>17-11-1981</hiredate>
<sub1>empid1-one</sub1>
empid="2"
<ename>BLAKE</ename>
<hiredate>1-5-1981</hiredate>
<sub1>empid2-one</sub1>
<sub2>empid2-two</sub2>

我希望得到的结果是...

empid="1"
<ename>KING</ename>
<sub1>empid1-one</sub1>
<hiredate>17-11-1981</hiredate>
empid="2"
<ename>BLAKE</ename>
<sub1>empid2-one</sub1>
<hiredate>1-5-1981</hiredate>
<sub2>empid2-two</sub2>

我希望结果顺序基于我的 return 子句的顺序。

有人能给我指出正确的方向吗?谢谢

实际上,XQuery 不会更改您指定的 return 值的顺序。您观察到的是由于您的代码在循环遍历 test 元素之前专门循环遍历所有 employee 元素,通过说 in $db/(/employees/employee,/employees/employee/test).

假设一个employee只能有一个testchild,你可以这样试试:

let $db := db:open("example", "documents/employee.xml")
for $item in $db/employees/employee
let $empid := $item/@empid
let $ename := $item/ename
let $sub1 := $item/test/sub1
let $hiredate := $item/hiredate
let $sub2 := $item/test/sub2
return ($empid,$ename,$sub1,$hiredate,$sub2)

har07 已经给出了很好的答案,采纳这个答案,不是我的。补充一点,没有父元素不能输出属性节点。您可以像这样更改属性变量:

let $empid := $item/@empid/concat(name(), '=', ., '&#10;')

如果您更关心换行符而不是纯空格行:

let $empid := $item/@empid/concat('&#10;',name(), '=', ., '&#10;')

输出将是

<?xml version="1.0" encoding="UTF-8"?>
empid=1
<ename>KING</ename>
<hiredate>17-11-1981</hiredate>
empid=2
<ename>BLAKE</ename>
<sub1>one</sub1>
<hiredate>1-5-1981</hiredate>
<sub2>two</sub2>

事实上,输出根本就不是 XML 并且有一个 XML 声明是没有意义的。使用

declare namespace output = "http://www.w3.org/2010/xslt-xquery-serialization";
declare option output:omit-xml-declaration "yes";

去掉声明。这应该适用于最新版本的 BaseX。然后,输出将是

empid=1
<ename>KING</ename>
<hiredate>17-11-1981</hiredate>
empid=2
<ename>BLAKE</ename>
<sub1>one</sub1>
<hiredate>1-5-1981</hiredate>
<sub2>two</sub2>