鉴于:
declare variable $seq := (
(('foo', 'bar'), ('baz'))
);
<result>{ ($seq[(.)[1][1] = 'foo'])[2][1] }</result>
我预计:
<result>baz</result>
但是得到:
</result>
为什么?
尽管看起来与此相反,XQuery 并不是 Lisp 的方言。(是的,我知道;如果是的话,世界上有些人会更快乐。)
XQuery 序列不嵌套,并且当给定的表达式似乎暗示嵌套时(如本查询中的那些),XQuery 求值器将序列展平。所以在你的例子中 $seq 的值是('foo','bar','baz')。
表达式$seq[(.)[1][1] = 'foo']
可以简化为$seq[. = 'foo']
并计算为序列'foo'
。
紧随其后的谓词[2]
并[1]
首先询问此序列中的第二项(保证产生长度为零或一的序列),然后询问结果序列中的第一项(这里保证完全没有效果) . 因为实际上这个序列'foo'
是一个单例,所以没有第二个成员。
因此 的值($seq[(.)[1][1] = 'foo'])[2][1]
是空序列,查询的值作为一个整体是一个空result
元素。
在 XQuery 中实现嵌套结构的最简单方法是使用 XML。XML 比较擅长嵌套结构,而 XQuery 非常擅长使用 XML。
在 XQuery 中,数组没有维度,因此(('foo', 'bar'), ('baz'))
与('foo', 'bar', 'baz')
.
($seq[(.)[1][1] = 'foo'])
与$seq[. = 'foo']
=>相同text{'foo'}
。这被视为长度为 1 的序列。所以(text{'foo'})[1]
=> text{'foo'}
,但(text{'foo'})[2]
显然是()
。