0

コードをシリアル化しようとしています。

XmlElement ASP.Netを使用してクラスメンバーのOrderプロパティを設定すると、この行で例外が発生しました。

XmlSerializer serializer = new XmlSerializer(typeof(HotelListResponse));

例外は;

一貫性のないシーケンス:クラスのメンバーの1つで使用する場合、すべてのパーティクルのようなメンバーで「Order」プロパティが必要です。クラスメンバー「_hotelId」でXmlElement、XmlAnyElement、またはXmlArrayカスタム属性を使用して「Order」を明示的に設定してください。

コードは次のとおりです。

 using (HttpWebResponse response = (HttpWebResponse)request.GetResponse())
             {

                 StreamReader responsereader = new  StreamReader(response.GetResponseStream());

                  var responsedata = responsereader.ReadToEnd();
                  xmldoc = (XmlDocument)JsonConvert.DeserializeXmlNode(responsedata);
                  xmldoc.Save(@"C:\New folder\myfile.xml");

                 DataTable dt = new DataTable();
                 DataRow dr;
                 dt.Columns.Add("hotelId");
                 dt.Columns.Add("name");
                 dt.Columns.Add("address1");
                 dt.Columns.Add("address2");
                 dt.Columns.Add("city");
                 dt.Columns.Add("postalCode");
                 dt.Columns.Add("countryCode");
                 dr = dt.NewRow();

                  XmlSerializer serializer = new XmlSerializer(typeof(HotelListResponse));

                 Stream reader = new FileStream(@"C:\New folder\myfile.xml", FileMode.Open);

                 HotelListResponse htype = (HotelListResponse)serializer.Deserialize(reader);
                 dt.ReadXml(@"C:\New folder\myfile.xml");
                 foreach(hoteltype ht in htype.hotel){
                      GridView1.DataSource = dt;
                      GridView1.DataBind();
                  }

                 //responsereader.Close();
                  //request.GetResponse().Close();

             }
         }
         catch (WebException ex)
         { 
             if (ex.Response == null)
                 throw new NullReferenceException("WebException response");
             throw ex;
         }

 }
    [System.SerializableAttribute()] 
    [System.Xml.Serialization.XmlRoot("HotelListResponse")]
     public class HotelListResponse
     {

         [System.Xml.Serialization.XmlElementAttribute("hotel")]
         public hoteltype[] hotel;
         [System.Xml.Serialization.XmlElement(Order = 0)] 
         public hoteltype[] Items {

             get {
                 return this.hotel;
             }
             set {
                 this.hotel = value;
             }
         } 
     }

    [Serializable]    
    [XmlType("hoteltype")]
    public class hoteltype
    {
        hoteltype(){}     

        public int _hotelId;  
        public string _name;   
        public string _address1;     
        public string _address2;    
        public string _city;
        public int _postalCode;  
        public string _countryCode;

        [XmlElement]
        public hoteltype[] htype;

        [System.Xml.Serialization.XmlElement(Order=1)]

        public int hotelId
        { 
            get {
                return _hotelId;
            } 
          set{
              _hotelId = value;
         }
      }
       [System.Xml.Serialization.XmlElement(Order=2)]

      public string name
    {
        get
        {
            return _name;
        }
        set
        {
            _name = value;
        }
    }
    [System.Xml.Serialization.XmlElement(Order=3)]

    public string address1
    {
        get
        {
            return _address1;
        }
        set
        {
            _address1 = value;
        }
    }
    [System.Xml.Serialization.XmlElement(Order=4)]

    public string address2
    {
        get
        {
            return _address2;
        }
        set
        {
            _address2 = value;
        }
    }
    [System.Xml.Serialization.XmlElement(Order=5)]

    public string city
    {
        get
        {
            return _city;
        }
        set
        {
            _city = value;
        }
    }
    [System.Xml.Serialization.XmlElement(Order=6)]

    public int postalCode
    {
        get
        {
            return _postalCode;
        }
        set
        {
            _postalCode = value;
        }
    }
    [System.Xml.Serialization.XmlElement(Order=7)]
    public string countryCode
    {
        get
        {
            return _countryCode;
        }
        set
        {
            _countryCode = value;
        }
    }  

}

4

1 に答える 1

2

例外で説明されているように、 を使用するとすぐOrder=xxに、クラスのシリアル化可能なすべてのプロパティとフィールドを順序付けする必要があります。ただし、_hotelIdプライベートな支援フィールドを意図していた可能性があるようです。XmlSerializerpublic フィールドもシリアル化するため、これは意図的ではない可能性があります。_hotelId本当に公開する必要があるが、シリアル化したくない場合は、を使用できますXmlIgnore

あなたのクラスは次のようになると思います:

[System.SerializableAttribute()] 
public partial class HotelListResponse 
{ 
    [System.Xml.Serialization.XmlElement(Order = 0)] 
    public string SomeOrderedField 
    { 
        get;
        set;
    } 

    // ** Problem may be here
    // Because the field is public, XmlSerializer will try to serialize this
    public int _hotelId; 

    [System.Xml.Serialization.XmlElement(Order = 1)] 
    public int HotelId
    { 
        get
        {
            return _hotelId;
        }
        set
        {
            _hotelId = value;
        }
    }

編集はい、まさにそれが問題です

バッキング フィールドをプライベートにします。そのため、public プロパティ アクセサーを用意しています。

    public int _hotelId;  => private int _hotelId;
    public string _name;  => private string _name;

編集

    [XmlElement(Order=0)]
    public hoteltype[] htype;

また、同時にプロパティに変更します。.NET 3.5 以降を使用している場合は、自動バッキング フィールドを使用します。

    [XmlElement(Order=0)]
    public hoteltype[] htype
    {
       get;
       set;
    }

編集

上記を体系的に適用すると、シリアライズ可能なクラスは次のようになります。

    [System.SerializableAttribute()]
    [System.Xml.Serialization.XmlRoot("HotelListResponse")]
    public class HotelListResponse
    {
        // This is bad practice - never make a backing field public
        //[System.Xml.Serialization.XmlElementAttribute("hotel")]
        //public hoteltype[] hotel;

        // Use the >= .Net 3.5 automatic properties - this way you don't need 
        // the backing field at all, which will prevent confusion over 
        // 'what gets serialized'
        [System.Xml.Serialization.XmlElement(Order = 0)]
        public hoteltype[] Items
        {
            get;
            set;
        }
    }

    [Serializable]
    [XmlType("hoteltype")]
    public class hoteltype
    {
        public hoteltype() { }

        [System.Xml.Serialization.XmlElement(Order = 0)]
        public hoteltype[] htype
        {
            get;
            set;
        }

        [System.Xml.Serialization.XmlElement(Order = 1)]
        public int hotelId
        {
            get;
            set;
        }
        [System.Xml.Serialization.XmlElement(Order = 2)]
        public string name
        {
            get;
            set;
        }

        [System.Xml.Serialization.XmlElement(Order = 3)]
        public string address1
        {
            get;
            set;
        }
        [System.Xml.Serialization.XmlElement(Order = 4)]
        public string address2
        {
            get;
            set;
        }
        [System.Xml.Serialization.XmlElement(Order = 5)]
        public string city
        {
            get;
            set;
        }
        [System.Xml.Serialization.XmlElement(Order = 6)]

        public int postalCode
        {
            get;
            set;
        }
        [System.Xml.Serialization.XmlElement(Order = 7)]
        public string countryCode
        {
            get;
            set;
        }
    }

そして、次のようなシリアル化/逆シリアル化サイクルを介して上記をテストします。

XmlSerializer serializer = new XmlSerializer(typeof(HotelListResponse));

HotelListResponse X = new HotelListResponse();
X.Items = new hoteltype[2];
X.Items[0] = new hoteltype();
X.Items[0].address1 = "address1";
X.Items[1] = new hoteltype();
X.Items[1].address1 = "address2";

using (Stream writer = new FileStream(@"C:\temp\myfile.xml", FileMode.Create))
{
    serializer.Serialize(writer, X);
    writer.Flush();
}

Stream reader = new FileStream(@"C:\temp\myfile.xml", FileMode.Open);

HotelListResponse htype = (HotelListResponse)serializer.Deserialize(reader);

次のファイルはデシリアライズします:

<?xml version="1.0"?>
<HotelListResponse xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <Items>
    <hotelId>0</hotelId>
    <address1>address1</address1>
    <postalCode>0</postalCode>
  </Items>
  <Items>
    <hotelId>0</hotelId>
    <address1>address2</address1>
    <postalCode>0</postalCode>
  </Items>
</HotelListResponse>
于 2013-01-15T14:08:00.477 に答える