Serialisierung in C# mit einer abgeleiteten Klasse

Baue ich eine Benachrichtigung Rahmen und dafür bin ich serialisieren und Deserialisieren eine Basisklasse, von der alle Klassen, die ich senden möchten, ableiten.

Das problem ist, dass der code kompiliert, aber wenn ich tatsächlich versuchen zu serialisieren Sie dieses basic-Klasse bekomme ich einen Fehler sagen

System.- Laufzeit.Serialisierung.SerializationException: Der Typ 'Xxx.DataContracts.WQAllocationUpdate' in Assembly 'Xxx.DataContract, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null " ist nicht als serialisierbar markiert.

Hier ist der code :

public class WCallUpdate : NotificationData
{
    private string m_from = "";
    [DataMember]
    public string From
    {
        get { return m_from; }
        set { m_from = value; }
    }
    private WCall m_wCall = new WCall();
    [DataMember]
    public WCall Call
    {
        get { return m_wCall; }
        set { m_wCall = value; }
    }
}

Den DataContract für die Benachrichtigung:

///<summary>
///Basic class used in the notification service
///</summary>
[DataContract]
public class NotificationData
{
}

///<summary>
///Enum containing all the events used in the application
///</summary>
[DataContract]
public enum NotificationTypeKey
{
    [EnumMember]
    Default = 0,
    [EnumMember]
    IWorkQueueServiceAttributionAddedEvent = 1,
    [EnumMember]
    IWorkQueueServiceAttributionUpdatedEvent = 2,
    [EnumMember]
    IWorkQueueServiceAttributionRemovedEvent = 3,
}

Code zum serialisieren der Daten ist:

    #region Create Message
    ///<summary>
    ///Creates a memoryStream from a notificationData
    ///note: we insert also the notificationTypeKey at the beginning of the
    ///stream in order to treat the memoryStream correctly on the client side
    ///</summary>
    ///<param name="notificationTypeKey"></param>
    ///<param name="notificationData"></param>
    ///<returns></returns>
    public MemoryStream CreateMessage(NotificationTypeKey notificationTypeKey, NotificationData notificationData)
    {
        MemoryStream stream = new MemoryStream();
        BinaryFormatter formatter = new BinaryFormatter();
        try
        {
            formatter.Serialize(stream, notificationTypeKey);
            formatter.Serialize(stream, notificationData);
        }
        catch (Exception ex)
        {
            Logger.Exception(ex);
        }
        return stream;
    }
    #endregion

Wenn ich versuche, um eine Nachricht zu erstellen:

WCallUpdate  m_wCallUpdate = new WCallUpdate();
NotificationTypeKey  m_notificationTypeKey = new NotificationTypeKey.Default;
CreateMessage(notificationTypeKey , wCallUpdate );

Bekam ich die folgende Fehlermeldung:

System.Runtime.Serialization.SerializationException: Type 'Xxx.DataContracts.WCall' in Assembly 'Xxx.DataContract, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null' is not marked as serializable.
   at System.Runtime.Serialization.FormatterServices.InternalGetSerializableMembers(RuntimeType type)
   at System.Runtime.Serialization.FormatterServices.GetSerializableMembers(Type type, StreamingContext context)
   at System.Runtime.Serialization.Formatters.Binary.WriteObjectInfo.InitMemberInfo()
   at System.Runtime.Serialization.Formatters.Binary.WriteObjectInfo.InitSerialize(Object obj, ISurrogateSelector surrogateSelector, StreamingContext context, SerObjectInfoInit serObjectInfoInit, IFormatterConverter converter, ObjectWriter objectWriter)
   at System.Runtime.Serialization.Formatters.Binary.WriteObjectInfo.Serialize(Object obj, ISurrogateSelector surrogateSelector, StreamingContext context, SerObjectInfoInit serObjectInfoInit, IFormatterConverter converter, ObjectWriter objectWriter)
   at System.Runtime.Serialization.Formatters.Binary.ObjectWriter.Write(WriteObjectInfo objectInfo, NameInfo memberNameInfo, NameInfo typeNameInfo)
   at System.Runtime.Serialization.Formatters.Binary.ObjectWriter.Serialize(Object graph, Header[] inHeaders, __BinaryWriter serWriter, Boolean fCheck)
   at System.Runtime.Serialization.Formatters.Binary.BinaryFormatter.Serialize(Stream serializationStream, Object graph, Header[] headers, Boolean fCheck)
   at System.Runtime.Serialization.Formatters.Binary.BinaryFormatter.Serialize(Stream serializationStream, Object graph)
   at Xxx.Notification.NotificationMessageFactory.CreateMessage(NotificationTypeKey notificationTypeKey, NotificationData notificationData) in Xxx.Notification\NotificationCenter.cs:line 36

Wenn ich das Serializable-flag vor der DataContract man das problem nicht lösen.


danke für die schnelle Antwort.
Sorry, dass ich vergessen habe, den code der NotificationData (bearbeitet in der main-post)

Ich versucht, indem Sie das Serializable-Attribut, um sowohl Klasse-ohne Erfolg 🙁

#region NotificationData
///<summary>
///Basic class used in the notification service
///</summary>
[Serializable]
[DataContract]
public class NotificationData
{
}
#endregion

und

[Serializable]
public class WCallUpdate : NotificationData
{
    private string m_from = "";
    [DataMember]
    public string From
    {
        get { return m_from; }
        set { m_from = value; }
    }
    private WCall m_wCall = new WCall();
    [DataMember]
    public WCall Call
    {
        get { return m_wCall; }
        set { m_wCall = value; }
    }
}

**Edit: * Mea culpa doch 🙂 Sie waren beide Recht.
Ich vergaß zu verbreiten [Serializable] - Attribut für alle die Kind-Klasse.
Nach der Aktualisierung und Zusammenstellung, ich habe nicht mehr die Ausnahme.
ich danke Ihnen beiden für Ihre Antworten zu korrigieren 🙂


@Marc Kies:
Eigentlich dachte ich über das, was Sie vorschlagen, und erstellt die folgenden DataContractSerializer, aber ich bin mir nicht sicher, ob dies funktionieren wird? Als meine Klassen nutzen andere Klassen? das große problem mit der DataContractSerializer ist, dass Sie brauchen, um zu geben Sie den Typ des Objekts, das Sie serialisieren möchten, und als meine Klasse andere Klasse, als die privaten Felder, die verursachen könnten ein problem genau?

#region DataContractSerializer
        ///<summary>
        ///Creates a Data Contract Serializer for the provided type. The type must be marked with
        ///the data contract attribute to be serialized successfully.
        ///</summary>
        ///<typeparam name="T">The type to be serialized</typeparam>
        ///<returns>A data contract serializer</returns>
        public static DataContractSerializer CreateDataContractSerializer<T>() where T : class
        {
            DataContractSerializer serializer = new DataContractSerializer(typeof(T));
            return serializer;
        }
        #endregion
Ich bin sehr verwirrt, warum Sie BinaryFormatter mit einem Daten-Vertrag (dieser Kommentar wird jetzt erweitert in einer Antwort).

InformationsquelleAutor srodriguez | 2009-04-16

Schreibe einen Kommentar