2014-02-13 54 views
1

我的類型A類:反序列化的NullReferenceException對象參考用類中的類

[Serializable] 
    public class TypeA 
    { 
    public string m_Title { get; set; } 

    [XmlIgnore] 
    public TypeB m_Target {get; set;} 

    public Int32 m_TypeBTargetID 
    { 
     get { return m_Target.m_ID; } 
     set 
     { //the ID is passed to a function that returns 
      //a specific TypeB that is in a list in the main thread 
      m_Target = FindTypeB(value); 
      m_TypeBTargetID= value; 
     } 
    } 

我公司主營:

public ObservableCollection<TypeA> A_Collection { get; set; } 
    public void DeSerializeTypeACollection() 
    { 
     try 
     { 
      XmlSerializer reader = new XmlSerializer(typeof(ObservableCollection<TypeA>)); 
      System.IO.TextReader file = new System.IO.StreamReader(
       @"c:\temp\myXML.xml"); 
      var d = reader.Deserialize(file); 
      A_Collection = (ObservableCollection<TypeA>)d; 
      file.Close(); 
     } 
     catch { } 
    } 

與集合中的一個元素序列化的結果,因此想我要序列:

<?xml version="1.0" encoding="utf-8"?> 
<ArrayOfTypeA xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema"> 
    <TypeA> 
    <m_Title>test2</m_Title> 
    <m_TypeBTargetID>32770</m_TypeBTargetID> 
    </TypeA> 
</ArrayOfTypeA> 

我得到的錯誤發生在var d = reader.Deserialize(fil E); 例外說,有XML文檔(3,2)中的一個錯誤是

<TypeA> 

它總是第一個元素的甚至20+的元素開始。

內部異常說NullReferenceException對象引用未設置爲對象的實例。

TypeA未被正確實例化清楚。至於爲什麼我有兩個理論。

我在TypeA中有其他變量也是私有的,但所有東西都在構造函數中實例化。我在某處讀反序列化不會調用構造函數,所以需要初始化的任何東西都需要在其他地方初始化。雖然我不確定。

或者:

至於類型B,類型B不能從類型A中被初始化。它需要FindTypeB(id)函數被調用,TypeB在程序的其他地方在一個特定的時刻構成(這發生在我反序列化注意你之前,所以我不認爲這是問題)。我認爲通過將它放在m_TypeBTargetID集合下可以解決這個問題,因爲它會被反序列化。也許這就是我的問題,而不是私有變量?

編輯:

堆棧Trace-

+  $exception {System.InvalidOperationException: There is an error in XML document (3, 4). ---> System.NullReferenceException: Object reference not set to an instance of an object. 
    at Application.TypeA.Shutdown() in TypeA.cs:line 150 
    at Application.TypeA.set_m_Enabled(Boolean value) in TypeA.cs:line 53 
    at Application.TypeA..ctor() in TypeA.cs:line 68 
    at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationReaderObservableCollection1.Read3_TypeA(Boolean isNullable, Boolean checkType) 
    at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationReaderObservableCollection1.Read4_ArrayOfTypeA() 
    --- End of inner exception stack trace --- 
    at System.Xml.Serialization.XmlSerializer.Deserialize(XmlReader xmlReader, String encodingStyle, XmlDeserializationEvents events) 
    at System.Xml.Serialization.XmlSerializer.Deserialize(TextReader textReader) 
    at Application.MainWindow.DeSerializeAlerts() in MainWindow.xaml.cs:line 393} System.Exception {System.InvalidOperationException} 
+0

請問你能分享堆棧跟蹤嗎?特別是InnerException。如果存在「內部異常」,則意味着當序列化程序位於第一個「TypeA」元素的末尾時發生了其他事情,並且它剛剛傳遞。 –

+0

你可以顯示你所有的'TypeA'類,尤其是'm_Enabled'屬性嗎? – JleruOHeP

+0

就是這樣。謝謝,我意識到我創建了一個特定的set屬性,它將調用Shutdown(),該屬性僅適用於m_Enabled爲false的情況。在這種情況下,m_Enabled默認爲false,因爲那是默認值。在我的無變量構造函數中,我將它初始化爲true,所以現在當反序列化器設置它時,它不會關閉()。我想給你信貸,所以只要你願意,就更新你的答案JleruOHeP。 Idk可能類似於「從設置m_Enabled」看看您的Shutdown():P – user99999991

回答

0

您的m_TypeBTargetID二傳手是相當strage。似乎你忘了你的私人變量...試試這個:

[Serializable] 
public class TypeA 
{ 
    public string m_Title { get; set; } 

    private TypeB _targetB 
    [XmlIgnore] 
    public TypeB m_Target 
    { 
    get //Do you need that setter? 
    { 
     if (_targetB == null) 
      _targetB = FindTypeB(m_TypeBTargetID); 

     return _targetB; 
    } 
    } 

    public Int32 m_TypeBTargetID {get; set;} 
} 
+0

嗯。你的設置看起來更清晰,但它仍然會拋出異常。我在TypeBTargetID下使用setter,認爲當它反序列化時,它會嘗試設置ID,然後我想讓它彈出FindTypeB。 – user99999991

+0

JleruOHeP指出我有另一個變量m_Enabled,它具有像Shutdown()這樣的自己設置的函數,只有在false時纔會調用它,並且永遠不會考慮解串器將其設置爲默認false。 – user99999991

相關問題