1

次の XML コード構造をシリアライズ/デシリアライズしようとしています。

<Person>
    <Name/>
    <Age/>
    <Address>
        <BuildingNumber/>
        <Street/>
        <Town/>
        <PostCode/>
    </Address>
</Person>

クラスの使用

public class Person {
    public string Name { get; set; }
    public int Age { get; set; }
    public Address Address { get; set; }
}

public class Address {
    public string BuildingNumber { get; set; }
    public string Street { get; set; }
    public string Town { get; set; }
    public string PostCode { get; set; }
}

私はIXmlSerializable両方のクラスで実装しています(この特定の例では過剰に設計されていますが、私が取り組んでいるかなり複雑なプロジェクトには必要です!)、シリアル化は正常に機能しますが、逆シリアル化は機能しません。

問題は、Person.ReadXml()私が次のように書いたメソッドで発生します。

public void ReadXml(XmlReader reader) {
    reader.ReadStartElement();
    if (!reader.IsEmptyElement) {
        Name = reader.ReadElementContentAsString("Name", string.Empty);
        Age = reader.ReadElementContentAsInt("Age", string.Empty);
        Address = (Address)reader.ReadElementContentAs(typeof(Address), null, "Address", string.Empty);
        // Also failed: Address = (Address)reader.ReadElementContentAsObject("Address", string.Empty);
    }
    reader.ReadEndElement();
}

初期化されている最後の行Addressは、例外をスローしています:

子要素を持つ要素で ReadElementContentAs() メソッドを呼び出すことはできません。(XmlException)

基本的に、を使用して子要素を持つ要素をどのように処理しIXmlSerializableますか?

4

2 に答える 2

3

ここで簡単に使用できると思いますXmlSerializer

XmlSerializer serializer = new XmlSerializer(typeof(Person));
Person person = (Person)serializer.Deserialize(reader);

シリアル化も非常に単純です。

serializer.Serialize(stream, person);

xml をカスタマイズする必要がある場合 (現在のケースではありません)、xml シリアライゼーション属性を使用してください。

于 2012-12-12T11:26:09.453 に答える
0

次のように試すことができます:

public void ReadXml(XmlReader reader)
{
    reader.MoveToContent();
    reader.ReadStartElement();
    Name = reader.ReadElementString("Name");
    Age = Convert.ToInt32(reader.ReadElementString("Age"));
    var xmlSerializer = new XmlSerializer(typeof (Address));
    Address = (Address) xmlSerializer.Deserialize(reader);
    reader.ReadEndElement();
}
  • 毎回アドレスの XmlSerializer を新しくするのは非効率的であり、キャッシュすることをお勧めします。
  • これは、アドレスが IXmlSerializable を実装しているかどうかに関係なく機能します。
  • 他の人が言ったように、IXmlSerializable は最後の手段としてのみ使用してください。属性が機能する場合は、はるかに優れた方法です。
于 2012-12-12T11:54:37.347 に答える