Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

.NET: How to binary serialize an object with attribute [DataContract]?

Tags:

.net

wcf

Class marked as [DataContract] can't be ISerializable at the same time. OK, so how can I serialize this type of object to a binary stream?

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

I can't make it work without Room being ISerializable. How can I get a byte array from object some other way?

like image 943
agnieszka Avatar asked Mar 04 '10 23:03

agnieszka


People also ask

What does the Datacontract attribute do?

Gets or sets a value that specifies whether to serialize the default value for a field or property being serialized.

What is Datacontract and DataMember in C#?

A datacontract is a formal agreement between a client and service that abstractly describes the data to be exchanged. In WCF, the most common way of serialization is to make the type with the datacontract attribute and each member as datamember.

How do you serialize binary?

In binary serialization, the public and private fields of the object and the name of the class, including the assembly containing the class, are converted to a stream of bytes, which is then written to a data stream. When the object is subsequently deserialized, an exact clone of the original object is created.

What is serializable attribute in C#?

This attribute is used in the class definition to indicate that a class can be serialized. By default, all fields in the class are serialized except for the fields that are marked with a NonSerializedAttribute . It is not necessary to use this attribute if a given type implements the System.


2 Answers

Code to serialize and deserialize using binary formatter:

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);
        }
    }
}

Usage:

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");
}
like image 70
Patrik Svensson Avatar answered Sep 22 '22 05:09

Patrik Svensson


The solution is to use DataContractSerializer to serialize the object.

like image 41
agnieszka Avatar answered Sep 20 '22 05:09

agnieszka