2010-03-04 17 views
6

Klasse, die als [DataContract] gekennzeichnet ist, kann nicht gleichzeitig ISerializable sein. OK, also wie kann ich diesen Objekttyp in einen binären Stream serialisieren?.NET: Wie binäre Serialisierung eines Objekts mit Attribut [DataContract]?

private byte[] GetRoomAsBinary(Room room) 
     { 
      MemoryStream stream = new MemoryStream(); 
      BinaryFormatter bf = new BinaryFormatter(); 
      bf.Serialize(stream, room); 
      return stream.ToArray(); 
     } 

Ich kann es nicht funktionieren lassen, ohne Raum ISerializable. Wie kann ich ein Byte-Array vom Objekt auf andere Weise bekommen?

Antwort

3

Die Lösung besteht darin, mit DataContractSerializer das Objekt zu serialisieren.

+0

'DataContractSerializer' erzeugt und liest XML. Und XML ist nicht binär. – picrap

0

Das ist das Prinzip der binären Serialisierung: nur [Serializable] -Klassen können serialisiert werden (obwohl ich gelesen habe, dass diese Einschränkung kürzlich aufgehoben wurde). Wenn Sie die Kontrolle über den Serialisierungsprozess übernehmen möchten, implementieren Sie ISerializable.

Wenn die Room-Klasse nicht serialisierbare Mitglieder hat, benötigen Sie ISerializable.

Was sind die Mitglieder von Room?

+0

, wie ich geschrieben habe: Sie haben eine Klasse nicht haben kann, die serializable und Datacontract ist gleichzeitig. dies wirft eine Ausnahme zur Laufzeit – agnieszka

+0

Sie haben Recht, ich habe die Frage missverstanden. – Timores

+0

Ist es akzeptabel, eine Kopie der Room-Klasse zu haben, sagen wir RoomProxy mit denselben Mitgliedern, serialisierbar, aber nicht an einem DataContract beteiligt? Um die Duplizierung zu vermeiden, könnte man eine Unterklasse von Room haben, die nicht als [DataContract] markiert ist; Es könnte serialisiert werden, indem ISerializable implementiert wird. – Timores

24

-Code zu serialisieren und deserialisieren binäre Formatierungsprogramm mit:

public static class BinarySerializer 
{ 
    public static byte[] Serialize<T>(T obj) 
    { 
     var serializer = new DataContractSerializer(typeof(T)); 
     var stream = new MemoryStream(); 
     using (var writer = 
      XmlDictionaryWriter.CreateBinaryWriter(stream)) 
     { 
      serializer.WriteObject(writer, obj); 
     } 
     return stream.ToArray(); 
    } 

    public static T Deserialize<T>(byte[] data) 
    { 
     var serializer = new DataContractSerializer(typeof(T)); 
     using (var stream = new MemoryStream(data)) 
     using (var reader = 
      XmlDictionaryReader.CreateBinaryReader(
       stream, XmlDictionaryReaderQuotas.Max)) 
     { 
      return (T)serializer.ReadObject(reader); 
     } 
    } 
} 

Verbrauch:

public void TestBinarySerialization() 
{ 
    // Create the person object. 
    Person person = new Person { Name = "John", Age = 32 }; 

    // Serialize and deserialize the person object. 
    byte[] data = BinarySerializer.Serialize<Person>(person); 
    Person newPerson = BinarySerializer.Deserialize<Person>(data); 

    // Assert the properties in the new person object. 
    Debug.Assert(newPerson.Age == 32); 
    Debug.Assert(newPerson.Name == "John"); 
} 
Verwandte Themen