Click here to Skip to main content
Click here to Skip to main content
Go to top

Deep Serialization: Binary and SOAP Serialization with a Generic Twist

, 22 Aug 2006
Rate this:
Please Sign up or sign in to vote.
A serialization class that you can include in your class library.

Introduction

You have one of the following problems:

  • You need to persist an object to a storage medium.
  • You are using RPC.
  • You need to stream to a socket.

The solution

Serialization allows you to convert a graph of objects into a linear sequence of bytes, XML, or SOAP. Once an object is flattened, you can store it or send it over the wire. Serialized data can then be deserialized. Deserialization essentially reconstitutes the graph of objects you initially serialized. Serialization sounds complicated, but in practice, it’s pretty easy because the .NET framework takes care of most of the complexity for you.

Microsoft's .NET framework provides two different options for persisting data or sending it over the network: shallow and deep serialization. Shallow serialization allows for the serialization of read-write property values of an object. Private data members and objects referenced by the object being serialized are ignored. Shallow serialization is used by Web Services and the XmlSerializer.

As you may have guessed from the title of this article, the focus of this code sample is on deep serialization. Deep serialization serializes the whole object and any objects referenced by the object being serialized. This code sample demonstrates how to serialize data using the BinaryFormatter and the SoapFormatter. Both of these classes perform deep serialization.

In order to be eligible for serialization, an object must be decorated with the [Serializable] attribute or implement the ISerializable interface. In the event that performance is an issue, you can opt to exclude a field in an object from serialization by decorating the field with the [NonSerialized] attribute—this is called selective serialization.

I've written the following code samples to demonstrate how easy it is to implement serialization in your project.

Step 1: binary serialization to a byte array

Binary serialization uses the BinaryFormatter which is contained in the System.Runtime.Serialization.Formatters.Binary namespace. The BinaryFormatter classes implement the IRemotingFormatter interface to support remote procedure calls (RPCs), and the IFormatter interface (inherited by the IRemotingFormatter) to support serialization of a graph of objects.

using System;
using System.Collections.Generic;
using System.IO;
using System.Runtime.Serialization.Formatters.Binary;

namespace CoreWebLibrary.Utility
{
   public static class BinarySerialization
   {
      public static byte[] BinarySerialize(Object obj)
      {
         byte[] serializedObject;
         MemoryStream ms = new MemoryStream();
         BinaryFormatter b = new BinaryFormatter();
         b.Serialize(ms, obj);
         ms.Seek(0, 0);
         serializedObject = ms.ToArray();
         ms.Close();
         return serializedObject;
      }

      public static T BinaryDeSerialize<T>(byte[] serializedObject)    
      {
         MemoryStream ms = new MemoryStream();
         ms.Write(serializedObject, 0, serializedObject.Length);
         ms.Seek(0, 0);
         BinaryFormatter b = new BinaryFormatter();
         Object obj = b.Deserialize(ms);
         ms.Close();
         return (T)obj;
      }
   }
}

Step 2: binary serialization to a file

An example of binary serialization to a file:

using System;
using System.Collections.Generic;
using System.IO;
using System.Runtime.Serialization.Formatters.Binary;

namespace CoreWebLibrary.Utility
{
   public static class FileSerialization
   {
      public static void FileSerialize(Object obj, string filePath)
      {
         FileStream fileStream = null;
         try
         {
            fileStream = new FileStream(filePath, FileMode.Create);
            BinaryFormatter b = new BinaryFormatter();
            b.Serialize(fileStream, obj);
         }
         catch
         {
            throw;
         }
         finally
         {
            if (fileStream != null)
               fileStream.Close();
         }
      }
      public static T FileDeSerialize<T>(string filePath)      
      {
         FileStream fileStream = null;
         Object obj;
         try
         {
            if (File.Exists(filePath) == false)
               throw new FileNotFoundException("The file" + 
                         " was not found.", filePath);
            fileStream = new FileStream(filePath, FileMode.Open);
            BinaryFormatter b = new BinaryFormatter();
            obj = b.Deserialize(fileStream);
         }
         catch
         {
            throw;
         }
         finally
         {
            if (fileStream != null)
               fileStream.Close();
         }
         return (T)obj;
      }
   }
}

Step 3: SOAP serialization to a string

SOAP serialization uses the SoapFormatter which is contained in the System.Runtime.Serialization.Formatters.Soap namespace. SOAP serialization is more versatile than binary serialization, but versatility comes at a significant cost in terms of performance.

Sample screenshot

using System;
using System.Collections.Generic;
using System.IO;
using System.Runtime.Serialization.Formatters.Soap;
using System.Text;

namespace CoreWebLibrary.Utility
{
   public class SoapSerialization
   {
      public static string SoapMemoryStreamSerialization(object obj, 
                           Encoding encodingType)
      {
         string xmlResult;
         using (Stream stream = new MemoryStream())
         {
            try
            {
               SoapFormatter sf = new SoapFormatter();
               sf.Serialize(stream, obj);
            }
            catch
            {
               throw;
            }
            stream.Position = 0;
            byte[] b = new byte[stream.Length];
            stream.Read(b, 0, (int)stream.Length);
            xmlResult = encodingType.GetString(b, 0, b.Length);
         }
         return xmlResult;
      }
      public T SoapDeserailization<T>(string input, 
               System.Text.Encoding encodingType)
      {
         Object obj = null;
         using (StringReader sr = new StringReader(input))
         {
            byte[] b;
            b = encodingType.GetBytes(input);
            Stream stream = new MemoryStream(b);
            try
            {
               SoapFormatter sf = new SoapFormatter();
               obj = (object)sf.Deserialize(stream);
            }
            catch
            {
               throw;
            }
         }
         return (T)obj;
      }
   }
}

Conclusion

Having an understanding of how serialization works is critically important if you want to be effective as a developer. Hopefully, this example has demonstrated that deep serialization is both easy to implement and powerful.

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here

Share

About the Author

Joseph Finsterwald
Web Developer
United States United States
Joseph Finsterwald lives in Boston, MA. For the past several years he has designed and implemented a number of enterprise applications for leading companies and academic institutions. He is fluent in a number of technologies, but his primary focus has been on .NET and object oriented development. He also has substantial experience in building both Sarbanes Oxley and CFR 21 part 11 compliant solutions. Joe has held positions at Barclays Global Investors, Boston Properties, Harvard Clinical Research Institute, Geonetics and Coreweb. He is currently working at mStyle as a senior engineer.

Comments and Discussions

 
Questionwhat about a button ? PinmemberDogu Tümerdem28-Aug-06 20:44 
GeneralMore generic serialization code Pinmembercraigd28-Aug-06 11:12 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.

| Advertise | Privacy | Mobile
Web04 | 2.8.140916.1 | Last Updated 23 Aug 2006
Article Copyright 2006 by Joseph Finsterwald
Everything else Copyright © CodeProject, 1999-2014
Terms of Service
Layout: fixed | fluid