tags:

views:

64

answers:

1

I have following piece of XML:

<items>
  <item type="simple">some text</item>
  <item type="complex"><b>other text</b></item>
</items>

I can define the "item" element with DTD, as:

<!ELEMENT item (#PCDATA|b)*>

How can I define it with XML Schema(XSD)?

A: 

XML schemas have these swell abstract types that make this thing pretty easy as long as having the xsi prefix on the type attribute in your actual XML doesn't bother you. You can define what you have above as follows:

  <!--items element-->
  <xs:element name="items">
    <xs:complexType>
      <xs:sequence>
        <xs:element ref="item" maxOccurs="unbounded" />
      </xs:sequence>
    </xs:complexType>
  </xs:element>

  <!--individual item element-->
  <xs:element name="item" type="item" />
  <!--make the item type abstract so you're forced to declare its type in the XML file-->
  <xs:complexType name="item" abstract="true" />

  <!--declare your simple type - mixed content is so that you can have text in a complex type-->
  <xs:complexType name="simple">
    <xs:complexContent mixed="true">
      <xs:extension base="item">
      </xs:extension>
    </xs:complexContent>
  </xs:complexType>

  <!--declare your complex type-->
  <xs:complexType name="complex">
    <xs:complexContent>
      <xs:extension base="item">
       <!--define the stuff that can go into that complex element-->
        <xs:sequence>
           <xs:element name="b" type="xs:string" />
        </xs:sequence>
      </xs:extension>
    </xs:complexContent>
  </xs:complexType>

And your resulting XML would be as follows:

<items xmlns="your-namespace" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"&gt;
  <item xsi:type="simple">some text</item>
  <item xsi:type="complex">
    <b>other text</b>
  </item>
</items>
barkimedes
It works just as you suggested. Very helpful.This solution seems using "abstract type" to define a group of elements, these elements are with same name, but different type of contents.
dqbai