XML Schema用于具有相同名称但属性值不同的元素序列?

8 xml xsd

如何为实例文档指定XML模式,如下所示:

<productinfo>
  <!-- other stuff -->
  <informationset type="Manufacturer">
    <!-- content not relevant -->
  </informationset>
  <informationset type="Ingredients">
    <!-- content not relevant -->
  </informationset>
</productinfo>
Run Code Online (Sandbox Code Playgroud)

也就是说,一个"productinfo"元素包含两个"信息集"子节点的序列,第一个有@type="Manufacturer"第二个,第二个有@type="Ingredients"

13r*_*ren 3

注意,正如 Serge 指出的那样,这个答案是不正确的。

使用xerces进行测试会出现此错误:cos-element-concienttype.xsd:3:21: cos-element-consistent: Error for type '#AnonType_productinfo'. Multiple elements with name 'informationset', with different types, appear in the model group.的规范中有更多详细信息。

但有一个解决方案,类似于下面 Marc 的答案,但仍然使用类型。如果它们位于由其他类型扩展的超类型的 minOccurs/maxOccurs 列表中,则不同类型的相同内容可能会多次出现。也就是说,就像 java 或 C# 中的多态类列表一样。这克服了上面的问题,因为虽然该元素名称可以在 xml 中出现多次,但它在 xsd 中只出现一次。

以下是 xsd 和 xml 示例 -这次使用xerces进行了测试!:

<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
  <xs:element name="productinfo">
    <xs:complexType>
      <xs:sequence>
        <xs:element name="informationset" type="supertype" minOccurs="2" maxOccurs="2"/>
      </xs:sequence>
    </xs:complexType>
  </xs:element>

  <xs:complexType name="supertype">
  </xs:complexType>

  <xs:complexType name="Manufacturer">
    <xs:complexContent>
      <xs:extension base="supertype">
      </xs:extension>
    </xs:complexContent>
  </xs:complexType>

  <xs:complexType name="Ingredients">
    <xs:complexContent>
      <xs:extension base="supertype">
      </xs:extension>
    </xs:complexContent>
  </xs:complexType>

</xs:schema>

<productinfo xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
  <informationset xsi:type="Manufacturer"></informationset>
  <informationset xsi:type="Ingredients"></informationset>
</productinfo>
Run Code Online (Sandbox Code Playgroud)

注意:您无法控制不同类型的顺序,或者每种类型出现的次数(每种类型可能出现一次、多次或根本不出现)——就像 java 或 C# 中的多态类列表一样。但您至少可以指定整个列表的确切长度(如果您愿意)。

例如,我将上面的示例限制为恰好两个元素,但未设置顺序(即制造商可以是第一个,或者成分可以是第一个);并且重复次数未设置(即它们可以都是Manufacturer,或者都是Ingredients,或者各一个)。


您可以使用 XML Schema type,如下所示:

<productinfo xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
  <informationset xsi:type="Manufacturer"></informationset>
  <informationset xsi:type="Ingredients"></informationset>
</productinfo>
Run Code Online (Sandbox Code Playgroud)

XSD 为每一种定义了单独的复杂类型:

<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
  <xs:element name="productinfo">
    <xs:complexType>
      <xs:sequence>
        <xs:element name="informationset" type="Manufacturer"/>
        <xs:element name="informationset" type="Ingredients"/>
      </xs:sequence>
    </xs:complexType>
  </xs:element>

  <xs:complexType name="Manufacturer">
  </xs:complexType>
  <xs:complexType name="Ingredients">
  </xs:complexType>
</xs:schema>
Run Code Online (Sandbox Code Playgroud)

这是 的一个特例xsi:type。一般来说,不要认为您可以在同名元素中指定具有不同值的属性,因为它们是同一元素的不同定义。

我不是 100% 清楚确切的原因 - 有人知道规范的相关部分吗?