2

我想创建一个具有以下约束的 XML 模式:

  • 根元素应为list.
  • list包含一组node元素。
  • 一个node元素可以有一个value属性。
  • 一个node元素可以包含一个value元素。
  • 一个node元素只能(并且恰好)具有一个value属性或value元素。

以下是验证上述约束的有效 XML 示例:

<?xml version="1.0" ?>
<list>
    <node id="1" value="A" />
    <node id="2">
        <value>B</value>
    </node>
</list>

我尝试了以下 XSD 架构:

<xs:schema attributeFormDefault="unqualified" elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema">
  <xs:element name="list">
    <xs:complexType>
      <xs:sequence>
        <xs:element name="node" maxOccurs="unbounded" minOccurs="0">
          <xs:complexType mixed="true">
            <xs:sequence>
              <xs:element type="xs:string" name="value" minOccurs="0"/>
            </xs:sequence>
            <xs:attribute type="xs:byte" name="id" use="optional"/>
            <xs:attribute type="xs:string" name="value" use="optional"/>
          </xs:complexType>
        </xs:element>
      </xs:sequence>
    </xs:complexType>
  </xs:element>
</xs:schema>

这个 XSD 模式验证了我的第一个和第二个约束,但不是第三个。

根据我的约束,以下 XML 示例无效,但是,它对我以前的 XSD 架构有效。

<?xml version="1.0" ?>
<list>
    <node id="2" value="A" /> <!-- valid -->
    <node id="4">
        <value>D</value>
    </node><!-- valid -->
    <node id="1" /><!-- not valid, missing value -->
    <node id="3" value="B">
        <value>C</value>
    </node><!-- not valid, both attribute and element are declared -->
</list>

如何更改我的架构以验证我的所有约束?

提前致谢。

4

2 回答 2

4

这在 XSD 1.0 中是不可能的。

XSD 1.1 应该可以使用断言:

<xs:assert test="not(@value and value)"/>

如果@value并且value两者都存在,则失败。要检查是否只有一个属性或子元素,请使用:

<xs:assert test="count((value, @value))=1"/>

正如迈克尔凯在评论中所建议的那样。

可以使用其他一些 XML 验证技术,例如 Schematron。

于 2013-05-21T15:41:41.467 回答
0

您可以创建具有必需属性的第一种类型和具有必需元素的第二种类型。然后使用包含这两种类型的选择合成器。

于 2015-01-29T09:52:48.013 回答