我向用户提供我们工作的工具,计算变量的可能性。值由给定的XPath表达式计算。在.Net中,使用Saxon库,可以通过在要计算的值的上下文中执行XPath表达式来计算值。
示例XML:
@data = '<Object>
<Parameters>
<Parameter Name="a">2</Parameter>
<Parameter Name="b">5</Parameter>
<Parameter Name="c"/>
</Parameters>
</Object>'
参数上下文中的XPath表达式,名称为&#34; c&#34;:
../Parameter[@Name="a"]/text() + ../Parameter[@Name="b"]/text()
这将导致7;)
我喜欢在SQL Server上执行XPath表达式,但现在想知道如何更改XML类型的上下文节点?
一种可能性是我在更改上下文的表达式前面添加了一个XPath,但是如果可能的话还没有找到。查询可能看起来像:
/<go to node variable "c" and make this the context node>
../Parameter[@Name="a"]/text() + ../Parameter[@Name="b"]/text()
有人有好主意吗?
答案 0 :(得分:1)
使用SQL Server的XQuery,您可以声明XQuery变量,例如$p
来引用目标父元素,即<Parameters>
,其中找到具有属性Name="c"
的子元素。然后,您可以使用$p
作为上下文元素进行进一步的XPath / XQuery处理:
declare @data XML = '<Object>
<Parameters>
<Parameter Name="a">2</Parameter>
<Parameter Name="b">5</Parameter>
<Parameter Name="c"/>
</Parameters>
</Object>'
SELECT @data.value('
let $p := /Object/Parameters[Parameter/@Name="c"]
return ($p/Parameter[@Name="a"])[1] + ($p/Parameter[@Name="b"])[1]
','int') AS Result
<强> sqlfiddle demo
强>
输出
7
答案 1 :(得分:1)
你想要的是 - AFAIK - 不可能......
尝试使用XPath表达式定义工作查询:
顺便说一下:你的例子在两个方面是错误的:XML中的Attributs没有@
- 标记,而结束参数标签缺少最终的&#34; s&#34; ... < / p>
DECLARE @data XML=
'<Object>
<Parameters>
<Parameter Name="a">2</Parameter>
<Parameter Name="b">5</Parameter>
<Parameter Name="c"/>
</Parameters>
</Object>';
--This will not work, because your parts are not singleton
--SELECT Context.Node.value('../Parameter[@Name="a"]/text() + ../Parameter[@Name="b"]/text()','int')
--FROM @data.nodes('/Object/Parameters/Parameter[@Name="c"]') AS Context(Node);
--This works, because I framed both parts with (...)[1]
SELECT Context.Node.value('(../Parameter[@Name="a"]/text())[1] + (../Parameter[@Name="b"]/text())[1]','int')
FROM @data.nodes('/Object/Parameters/Parameter[@Name="c"]') AS Context(Node);
但是可能有一种解决方法,但它非常黑客且不可靠:
存储过程创建一个根据您的参数构建的动态sql语句并执行它。
您的必须不会更改的 XPath表达式将会更改为+
左侧和右侧的空白(以及{{} 1}},-
和*
)被替换为返回单例表达式。我不知道计算有多复杂。看看......
/