[英]XQuery how to filter nodes & its child nodes
如何从“ for”中循环的节点中仅选择前2个子节点
例如,我有这个xml,我需要选择合格的“是”人,我只想要他的前2个关联。 我的输出应该是带有过滤节点的相同XML结构。 我知道这对于XSLT来说是简单的任务,但是只是想知道XQuery是否有一种简单的方法。
<?xml version="1.0" encoding="UTF-8"?>
<Persons>
<Person>
<Name>Sam</Name>
<DOB>12-2-1981</DOB>
<Qualified>Yes</Qualified>
<Assosiation>
<Code>1</Code>
<Descreption>Assosiatoin1</Descreption>
</Assosiation>
<Assosiation>
<Code>2</Code>
<Descreption>Assosiatoin2</Descreption>
</Assosiation>
<Assosiation>
<Code>3</Code>
<Descreption>Assosiatoin3</Descreption>
</Assosiation>
<Assosiation>
<Code>4</Code>
<Descreption>Assosiatoin4</Descreption>
</Assosiation>
<Assosiation>
<Code>5</Code>
<Descreption>Assosiatoin5</Descreption>
</Assosiation>
<Assosiation>
<Code>6</Code>
<Descreption>Assosiatoin6</Descreption>
</Assosiation>
<Assosiation>
<Code>7</Code>
<Descreption>Assosiatoin7</Descreption>
</Assosiation>
<DynamicElement>Unkown</DynamicElement>
</Person>
<Person>
<Name>James</Name>
<DOB>12-2-1975</DOB>
<Qualified>No</Qualified>
<Assosiation>
<Code>1</Code>
<Descreption>Assosiatoin1</Descreption>
</Assosiation>
<Assosiation>
<Code>2</Code>
<Descreption>Assosiatoin2</Descreption>
</Assosiation>
<Assosiation>
<Code>3</Code>
<Descreption>Assosiatoin3</Descreption>
</Assosiation>
<Assosiation>
<Code>4</Code>
<Descreption>Assosiatoin7</Descreption>
</Assosiation>
<DynamicElement>Unkown</DynamicElement>
</Person>
<Person>
<Name>Jon</Name>
<DOB>12-2-1983</DOB>
<Qualified>Yes</Qualified>
<Assosiation>
<Code>1</Code>
<Descreption>Assosiatoin1</Descreption>
</Assosiation>
<Assosiation>
<Code>2</Code>
<Descreption>Assosiatoin2</Descreption>
</Assosiation>
<Assosiation>
<Code>3</Code>
<Descreption>Assosiatoin3</Descreption>
</Assosiation>
<Assosiation>
<Code>4</Code>
<Descreption>Assosiatoin7</Descreption>
</Assosiation>
<DynamicElement>Unkown</DynamicElement>
</Person>
</Persons>
非XQuery Update解决方案:
element Persons {
for $person in $xml/Persons/Person
where $person/Qualified = 'Yes'
return element Person {
$person/Name,
$person/DOB,
$person/Qualified,
$person/Assosiation[position() = (1,2)],
$person/DynamicElement
}
}
如果您希望对其他元素的名称不那么具体:
element Persons {
for $person in $xml/Persons/Person
where $person/Qualified = 'Yes'
return element Person {
for $element in $person/*
return
$element[
local-name($element) != 'Assosiation' or
count($element/preceding-sibling::Assosiation) < 2
]
}
}
由于Oracle 11.2.0.3.0,Oracle还支持XQuery Update ,这是在这种情况下使用的正确工具。
XQuery本身不处理XML数据,因此您将需要重建完整的树,而只保留不需要的节点。 使用XQuery Update,您可以修改XML,从而仅删除不需要的节点:
copy $c := .
modify
for $p in $c//Person[Qualified = "Yes"][position() > 2]
return delete node $p
return $c
但是,在示例数据中,只有两个<Person />
元素,且Qualified设置为Yes,因此不会删除任何内容。 如果您要说的是要使用前两个元素,而仅将Qualified设置为Yes,则必须交换谓词,即$c//Person[position() > 2][Qualified = "Yes"]
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.