2011-10-28 5 views
5

私は以下のXML構造を持っています。XmlSerializerで使用するオプションのXML要素のクラスメンバーを装飾/定義する方法は?

<theElement attrOne="valueOne" attrTwo="valueTwo"> 
    <theOptionalList> 
     <theListItem attrA="valueA" /> 
     <theListItem attrA="anotherValue" /> 
     <theListItem attrA="stillAnother" /> 
    </theOptionalList> 
</theElement> 
<theElement attrOne="anotherOne" attrTwo="anotherTwo" /> 

対応するクラスの構造を表現するクリーンな方法は何ですか:theElement要素はtheOptionalList要素、あるいはませんが含まれていることができますか?

私は次のかなり確信している:theElementため

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 
using System.Xml.Serialization; 

namespace MyNamespace 
{ 
    public class TheListItem 
    { 
     [XmlAttributeAttribute("attrA")] 
     public string AttrA { get; set; } 

     public override string ToString() 
     { 
      StringBuilder outText = new StringBuilder(); 

      outText.Append(" attrA = " + AttrA + "\r\n");     
      return outText.ToString(); 
     } 
    } 
} 

しかし、何について:

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 
using System.Xml.Serialization; 

namespace MyNamespace 
{ 
    public class TheOptionalList 
    { 
     [XmlAttributeAttribute("attrOne")] 
     public string AttrOne { get; set; } 

     [XmlAttributeAttribute("attrTwo")] 
     public string AttrTwo { get; set; } 

     [XmlArrayItem("theListItem", typeof(TheListItem))] 
     public TheListItem[] theListItems{ get; set; } 

     public override string ToString() 
     { 
      StringBuilder outText = new StringBuilder(); 

      outText.Append("attrOne = " + AttrOne + " attrTwo = " + AttrTwo + "\r\n"); 

      foreach (TheListItem li in theListItems) 
      { 
       outText.Append(li.ToString()); 
      } 

      return outText.ToString(); 
     } 
    } 
} 

と同様に? theOptionalList要素を配列型として取り込み、ファイル内で何が見つかったのか(何もないものも)を読み取って、そのコードが存在するかどうかをコードでチェックしますか?それとも私が提供できる別のデコレータがありますか?それともちょうどうまくいくのですか?

編集:私はthis answerからの情報を使用して終了しました。

答えて

5

XmlArrayItem属性にIsNullable = trueを追加してみてください。

+0

応答ジェームズありがとう。私はこれが要素を持たない 'theOptionalList'要素を扱うだろうと思っていますが、' theOptionalList'は全く存在しません。 (私はあなたが示唆していることを理解していないかもしれません。)また、私のフォーマットのためのスキーマはありません。私と他の開発者との間では口頭で合意しています。:) – John

+0

は、私は肯定的ではないんだけど、私は、配列がnullの場合、 'IsNullable'はそれを排除する使用と思います。 –

+1

スキーマを検討してください。それは大いに役立ちますが、小さくても、あなたの「ツールキット」にとっては素晴らしい作品です。 – Gusdor

4

要素を含めるかどうかを指定するために別のブールを使用できるようです。

別のオプションは、XmlSerializerをによって認識ブールフィールド を作成するために特殊なパターンを使用して、フィールドにXmlIgnoreAttribute を適用することです。パターンは、 propertyNameSpecifiedの形式で作成されます。たとえば、 "MyFirstName"という名前のフィールドがある場合は、 "MyFirstNameSpecified"というフィールドを作成し、XmlSerializerに という名前のXML要素を生成するかどうかを指示します。これは、次の例の に示されています。

public class OptionalOrder 
{ 
    // This field should not be serialized 
    // if it is uninitialized. 
    public string FirstOrder; 

    // Use the XmlIgnoreAttribute to ignore the 
    // special field named "FirstOrderSpecified". 
    [System.Xml.Serialization.XmlIgnoreAttribute] 
    public bool FirstOrderSpecified; 
} 

http://msdn.microsoft.com/en-us/library/system.xml.serialization.xmlserializer.aspx

+0

おかげで方法もあります。この例では、私が直面していることの一部であるシリアル化を扱います。もう1つはデシリアライズです。この形式のファイルに対して 'Deserialize()'を呼び出すとどうなりますか?なぜなら、要素ごとに何を期待するのか、ファイルの 'XmlSerializer'を伝えることはできないと思うからです。つまり、デシリアライズしてクラスに指定されたメンバーが表示されない場合、デフォルトの動作がありますか? – John

+0

はい、デフォルトの動作があります:クラスのデフォルトのコンストラクタです。 XMLを逆シリアル化すると、 'XMLSerializer'はデフォルトのコンストラクタを呼び出してオブジェクトを作成します。ここでデフォルトを設定できます。デフォルトのコンストラクタでプロパティのデフォルトを設定し、他のコンストラクタに ':this()'を追加すると、デフォルトが最初に設定されるようになります。 – JCH2k

0

XxySpecifed財産への追加、応答のためのShouldSerialize接頭

[XmlElement] 
public List<string> OptionalXyz {get; set;} 

public bool ShouldSerializeOptionaXyz() { 
    return OptionalXyz != null && OptionalXyz.Count > 0 ; 
} 
関連する問題