Представление повторяющейся пары XML-элементов в XSD

В настоящее время у меня проблема с XSD. Обычно запись выглядит так:

<Entry Num="4">
    <Info>
        <Name>Something</Name>
        <ID>1234</ID>
        <Start>2013-01-07</Start>
        <Stop>2013-01-09</Stop>
        <Completed>6</Completed>
    </Info>
</Entry>

Но иногда это будет выглядеть так:

<Entry Num="5">
    <Info>
        <Name>SomethingElse</Name>
        <ID>5678</ID>
        <Start>2013-01-08</Start>
        <Stop>2013-01-10</Stop>
        <Start>2013-01-11</Start>
        <Stop>2013-01-12</Stop>
        <Completed>14</Completed>
    </Info>
</Entry>

Чтобы попытаться использовать потенциал для нескольких запусков и остановок, я пробовал следующие вещи:

<xs:sequence maxOccurs="unbounded">
    <xs:element name="Start" type="xs:dateTime" maxOccurs="1"/>
    <xs:element name="Stop" type="xs:dateTime" maxOccurs="1"/>
</xs:sequence>

<xs:sequence maxOccurs="unbounded">
    <xs:element name="Start" type="xs:dateTime" />
    <xs:element name="Stop" type="xs:dateTime" />
</xs:sequence>

<xs:sequence maxOccurs="unbounded">
    <xs:sequence>
        <xs:element name="Start" type="xs:dateTime" />
        <xs:element name="Stop" type="xs:dateTime" />
    </xs:sequence>
</xs:sequence>

<xs:sequence maxOccurs="unbounded">
    <xs:sequence>
        <xs:element name="Start" type="xs:dateTime" maxOccurs="1"/>
        <xs:element name="Stop" type="xs:dateTime" maxOccurs="1"/>
    </xs:sequence>
</xs:sequence>

Но все они привели к массиву Starts, который печатается, за которым следует массив Stops, когда я преобразовал его в классы C # с помощью xsd.exe, который сериализуется в это:

<Entry Num="5">
    <Info>
        <Name>SomethingElse</Name>
        <ID>5678</ID>
        <Start>2013-01-08</Start>
        <Start>2013-01-11</Start>
        <Stop>2013-01-10</Stop>
        <Stop>2013-01-12</Stop>
        <Completed>14</Completed>
    </Info>
</Entry>

И это не соответствует файлу XML. Кто-нибудь знает, как сделать что-то подобное правильно? Большое спасибо.

Я придумал решение, которое работает, но не идеально.

Текущее решение:

<xs:choice minOccurs="2" maxOccurs="unbounded">
    <xs:element name="Start" type="xs:dateTime"/>
    <xs:element name="Stop" type="xs:dateTime"/>
</xs:choice>

person Josiah Witt    schedule 24.10.2013    source источник


Ответы (1)


Вы просто пропустили аргумент /order.

Попробуйте что-то вроде этого: xsd /c /order your.xsd

Результат будет отличаться от того, что у вас есть, благодаря дополнительным значениям Order:

[System.Xml.Serialization.XmlElementAttribute("Start", typeof(System.DateTime), DataType="date", Order=2)]
[System.Xml.Serialization.XmlElementAttribute("Stop", typeof(System.DateTime), DataType="date", Order=2)]
[System.Xml.Serialization.XmlChoiceIdentifierAttribute("ItemsElementName")]
public System.DateTime[] Items {
    get {
        return this.itemsField;
    }
    set {
        this.itemsField = value;
    }
}

Простая тестовая программа, подобная этой, правильно обработает ваш XML:

using System;
using System.IO;
using System.Xml.Serialization;

namespace ConsoleApplication2
{
    class Program
    {
        static void Main(string[] args)
        {
            XmlSerializer ser = new XmlSerializer(typeof(Entry));
            Entry o;
            using (Stream s = File.OpenRead(@"D:\...\representing-a-repeated-pair-of-xml-elements-in-xsd-2.xml"))
            {
                o = (Entry)ser.Deserialize(s);
            }
            using (Stream s = File.OpenWrite(@"D:\...\representing-a-repeated-pair-of-xml-elements-in-xsd-3.xml"))
            {
                ser.Serialize(s, o);
            }
        }
    }
}
person Petru Gardea    schedule 25.10.2013