2013-02-08 76 views
5

我試圖反序列化下面的XML:反序列化XML返回null集合屬性

<?xml version="1.0" encoding="utf-8" ?> 
<mf:somedata xmlns:mf="urn:somedata"> 
    <CurrentAccount> 
     <AccountType>test</AccountType> 
     <Charge> 
      <ChargeType>test</ChargeType> 
     </Charge> 
    </CurrentAccount> 
    <CurrentAccount> 
     <AccountType>test 2</AccountType> 
     <Charge> 
      <ChargeType>test 2</ChargeType> 
     </Charge> 
    </CurrentAccount> 
</mf:somedata> 

使用以下類:

[XmlRoot("somedata", Namespace = "urn:somedata")] 
public class MfCurrentAccounts 
{ 
    [XmlElement("CurrentAccount")] 
    public CurrentAccount[] CurrentAccounts { get; set; } 
} 

public class CurrentAccount 
{ 
    public string AccountType { get; set; } 

    [XmlElement("Charge")] 
    public Charge[] Charges { get; set; } 
} 

public class Charge 
{ 
    public string ChargeType { get; set; } 
} 

var c = new XmlSerializer(typeof(MfCurrentAccounts)).Deserialize(new StringReader(xml)) as MfCurrentAccounts; 

c.CurrentAccounts // <-- is always null 

但無論我怎麼努力,該CurrentAccounts陣列null當我反序列化它。我試過每個組合都可以考慮的屬性(我也試過XmlArray和XmlArrayItem)。

我在做什麼錯? :S

+0

對不起,用反序列化代碼更新了問題。 – Tom 2013-02-08 19:38:07

+0

你不需要用'[Serializable()]'標記類嗎? – Nope 2013-02-08 19:38:57

+0

@François我已經嘗試過,但顯然不需要。 – Tom 2013-02-08 19:39:31

回答

2

的問題是與命名空間。

當我在測試環境中創建整個班級設置時,我得到了一個非常不同的輸出結果。這裏是我想你應該嘗試閱讀:

<?xml version="1.0"?> 
    <mf:somedata xmlns:mf="urn:somedata"> 
     <mf:CurrentAccount> 
      <mf:AccountType>something 1</mf:AccountType> 
      <mf:Charge> 
       <mf:ChargeType>Charge Type 1</mf:ChargeType> 
      </mf:Charge> 
     </mf:CurrentAccount> 
     <mf:CurrentAccount> 
      <mf:AccountType>something 2</mf:AccountType> 
      <mf:Charge> 
       <mf:ChargeType>Charge Type 2</mf:ChargeType> 
      </mf:Charge> 
     </mf:CurrentAccount> 
    </mf:somedata> 

通知所有額外mf:。在聲明名稱空間時,序列化程序將與該名稱空間一起使用,並且僅反序列化正確屬於該名稱空間的節點。你要麼完全擺脫它,要麼適當地修正你的輸入。這裏是我用來生成輸出記下代碼:類定義是完全不變

XmlSerializer ser = new XmlSerializer(typeof(MfCurrentAccounts)); 
XmlSerializerNamespaces ns = new XmlSerializerNamespaces(); 
ns.Add("mf", "urn:somedata"); 

MemoryStream ms = new MemoryStream(); 
ser.Serialize(ms, a, ns); 

,並在閱讀它的時候回:運行兩部分後

ms.Position = 0; 
b = ser.Deserialize(ms) as MfCurrentAccounts; 

,B現在是一個完美的克隆,和我上面顯示的XML是生成的XML。

+0

謝謝你。不幸的是,XML來自第三方,所以我無法控制它。我試圖把它添加到CurrentAccounts屬性中:'[XmlElement(「CurrentAccount」,Namespace =「urn:somedata」)]'但無濟於事。 – Tom 2013-02-08 21:34:34

+0

您可以在嘗試反序列化之前編輯xml嗎?如果你在第一行使用了一些正則表達式,並且從頂部節點中刪除了「mf:」,那麼你將有一個統一的classdef,它應該正確反序列化...... – Nevyn 2013-02-08 22:49:48

+1

@Tom你有沒有試過[XmlElement(「CurrentAccount」,Namespace = String.Empty)]? – jbl 2013-02-08 22:50:17

0

也許你應該嘗試更換您的MfCurrentAccounts類:

[XmlRoot("somedata", Namespace = "urn:somedata")] 
public class MfCurrentAccounts : List<CurrentAccount> 
{ 
    public MfCurrentAccounts():base() 
    {} 

} 

或給看看https://stackoverflow.com/a/364410/1236044

希望這將有助於

+0

這只是返回一個空的列表。 :(儘管我會玩弄它,因爲它看起來應該可以工作,我會看看寫入磁盤和使用XSD文件,但我寧願不沿着這條路線前進。 – Tom 2013-02-08 21:45:55

+0

@Tom the類可能需要一個公共的構造函數。我更新了我的答案 – jbl 2013-02-08 21:55:26

+0

這似乎也沒有工作,但您對上一個答案的評論。:) – Tom 2013-02-09 10:17:05