"太多的物品"使用XPath eq运算符进行断言

时间:2014-09-20 13:29:26

标签: xml xpath xsd xpath-2.0

在针对XML架构验证以下XML文件时遇到问题。错误是“太多项目预期'1','3'被提供。在断言中我想表达以下内容:每当OID值等于BOID值时,A_Membership_Degree应该大于或等于B_Membership_Degree

示例XML

<Document xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="gen.xsd">
<A OID="AA" A_Membership_Degree="0.7" D_Membership_Degree="0.5"  >
  <A1>X1</A1>
  <A2>D1</A2>
 </A>
  <B BOID="AA" B_Membership_Degree="0.2">
  <B1>G1</B1>
  <B2>F1</B2>
 </B>
  <C  COID="AA" C_Membership_Degree="0.3" >
  <C1>G2</C1>
  <C2>F2</C2>
 </C>
<A OID="AAA" A_Membership_Degree="0.8" D_Membership_Degree="0.5"  >
  <A1>X2</A1>
  <A2>D2</A2>
 </A>
  <B BOID="AAA" B_Membership_Degree="0.5"  >
  <B1>G3</B1>
  <B2>F3</B2>
 </B>
 <C  COID="AAA" C_Membership_Degree="0.4" >
  <C1>G4</C1>
  <C2>F4</C2>
 </C>
 <A OID="HHH" A_Membership_Degree="0.8" D_Membership_Degree="0.5"  >
  <A1>X11</A1>
  <A2>D11</A2>
 </A>
 </Document>

当前架构

<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" 
           xmlns:vc="http://www.w3.org/2007/XMLSchema-versioning" 
           elementFormDefault="qualified" 
           attributeFormDefault="unqualified" 
           vc:minVersion="1.1">
  <xs:element name="Document">
    <xs:complexType>
      <xs:sequence maxOccurs="unbounded">
        <xs:element ref="A" minOccurs="0" maxOccurs="unbounded"/>
        <xs:element ref="B" minOccurs="0" maxOccurs="unbounded"/>
        <xs:element ref="C" minOccurs="0" maxOccurs="unbounded"/>
      </xs:sequence>
      <xs:assert 
        test="if(.//@OID eq  .//@BOID) 
              then ./A/@A_Membership_Degree  
                   ge ./B/@B_Membership_Degree else false()"/>
    </xs:complexType>
    <xs:key name="aKey">
      <xs:selector xpath="A"/>
      <xs:field xpath="@OID"/>
    </xs:key>
    <xs:keyref name="aKeyRef" refer="aKey">
      <xs:selector xpath="./B"/>
      <xs:field xpath="@BOID"/>
    </xs:keyref>
    <xs:keyref name="aKeyRef1" refer="aKey">
      <xs:selector xpath="./C"/>
      <xs:field xpath="@COID"/>
    </xs:keyref>
  </xs:element>
  <xs:element name="A" type="Atype"/>
  <xs:complexType name="Atype">
    <xs:sequence minOccurs="0" maxOccurs="unbounded">
      <xs:element name="A1" type="xs:string" minOccurs="1" maxOccurs="1"/>
      <xs:element name="A2" type="xs:string" minOccurs="1" maxOccurs="1"/>
    </xs:sequence>
    <xs:attribute name="OID" type="xs:string" use="required"/>
    <xs:attribute name="A_Membership_Degree" type="FuzzyValue" use="optional"/>
    <xs:attribute name="D_Membership_Degree" type="FuzzyValue" use="optional"/>
  </xs:complexType>
  <xs:element name="B" type="Btype"/>
  <xs:complexType name="Btype">
    <xs:sequence>
      <xs:element name="B1" type="xs:string" minOccurs="1" maxOccurs="1"/>
      <xs:element name="B2" type="xs:string" minOccurs="1" maxOccurs="1"/>
    </xs:sequence>
    <xs:attribute name="BOID" type="xs:string" use="required"/>
    <xs:attribute name="B_Membership_Degree" type="FuzzyValue" use="optional"/>
  </xs:complexType>
  <xs:element name="C" type="Ctype"/>
  <xs:complexType name="Ctype">
    <xs:sequence>
      <xs:element name="C1" type="xs:string" minOccurs="1" maxOccurs="1"/>
      <xs:element name="C2" type="xs:string" minOccurs="1" maxOccurs="1"/>
    </xs:sequence>
    <xs:attribute name="COID" type="xs:string" use="required"/>
    <xs:attribute name="C_Membership_Degree" type="FuzzyValue" use="required"/>
  </xs:complexType>
  <xs:simpleType name="FuzzyValue">
    <xs:restriction base="xs:decimal">
      <xs:minInclusive value="0"/>
      <xs:maxInclusive value="1"/>
    </xs:restriction>
  </xs:simpleType>
</xs:schema>

2 个答案:

答案 0 :(得分:1)

在XPath条件表达式中,else子句不是可选的。因此添加else false()可能是最简单的修复方法。

有些读者(包括我)可能会更清楚地将断言重新表述为明显的布尔值:

not(.//@OID eq .//@BOID)
or
(./A/@Membership_Degree ge ./B/@A_Membership_Degree)

但清晰度通常在旁观者眼中;你应该用自己的成语写下你的代码的预期读者最清楚。

答案 1 :(得分:0)

此特定错误的原因是eqge运算符期望它们的参数是单个值,但是您为它们提供了一组多个节点。而不是简单的if,你需要一个像这样的显式量化表达式

every $a in A, $b in B[@BOID eq $a/@OID] satisfies
    $a/@A_Membership_Degree ge $b/@B_Membership_Degree

这对in子句基本上生成一个A和一个B的匹配ID的列表,satisfies子句检查每对的隶属度条件。