Welcome to Jordev Sign in | Join | Help
C# 3.0: Automatic Properties and Serialization Problem

In the last post I talked about the Automatically Implemented Properties which is very cool productivity feature, and I talked a little bit about the underlying auto generated backing fields, since the post, I tried to play with the auto generated fields to find out a way to write the backing field name in the C# directly, the backing field looks like:

<Name>k__BackingField

 

The <Name> syntax is not allowed to be used with the C# identifiers, C# 3.0 compiler architects go with this in order not to conflict with any other fields written by the developer.

Now what about the serialization, let's say that I want to add some rules and validation to the getter and setter after implementing it, what will happen to the pre-serialized files after modifying the properties to the old pattern?

When using XML/SOAP serialization we don’t have to think a lot about the effects of the new change, but if we are using the Binary serialization then I think we are in a big troubleL!!!

The main difference between the XML and the Binary serialization is that the Binary serialization creates a byte for byte copy of the object's memory image and persist it to the disk which means that the serialized data contains all the members of the object, no matter if they are private or public in addition to the CLR types and the versioning information…which is our problem.

Here's an example serializable class that I will use it to demonstrate this case:

namespace Properties.AutoImplemented

{

    [Serializable]

    public class JordevMember

    {

 

        //Read Only Property

        public string Name { get; set; }

        //Write Only Property

        public string Job { get; set; }

        public string Email { get; set; }

        public DateTime DateOfBirth { get; set; }

 

    }

}

 

 

Here's a trivial implementation of the serialization and deserialization process using the classes included in the Framework:

/// <summary>

/// This method serialize instance of JordevMember with sample data...

/// </summary>

public static void SerializeJordevMember()

{

    //Definning instance of JordevMember class...

    JordevMember jdvMember = new JordevMember();

 

    //Filling JordevMember instance with sample data...

    jdvMember.Name = "Ammar";

    jdvMember.Job = "Software Engineer";

    jdvMember.Email = "Ammar@jordev.net";

 

    FileStream fs = new FileStream(@"c:\JordevMemberData.bin", FileMode.Create);

    BinaryFormatter bf = new BinaryFormatter();

   

    try

    {

        //Serializing binary image of the JordevMember object

        bf.Serialize(fs,jdvMember); 

    }

    catch (SerializationException ex)

    {

        Console.WriteLine("Serialization Failed because: " + ex.Message);

    }

    finally

    {

        fs.Close();

    }

}

 

    /// <summary>

    /// This method Deserialize the presisited instance of JordevMember class...

    /// </summary>

    public static void DeserializeJordevMember()

    {

       

        //Definning instance of JordevMember class...

        JordevMember jdvMember = new JordevMember();

 

        FileStream fs = new FileStream(@"c:\JordevMemberData.bin", FileMode.Open);

        BinaryFormatter bf = new BinaryFormatter();

 

        try

        {

            //Deserializing binary image of the JordevMember object

            jdvMember = (JordevMember)bf.Deserialize(fs); 

            Console.WriteLine("Jordev Member Name  : " + jdvMember.Name);

            Console.WriteLine("Jordev Member Job   : " + jdvMember.Job);

            Console.WriteLine("Jordev Member Email : " + jdvMember.Email);

        }

        catch (SerializationException ex)

        {

            Console.WriteLine("Deserialization Failed because: " + ex.Message);

        }

        finally

        {

            fs.Close();

        }

 

    }

 

And now let's take a look to the JordevMemberData.bin contents:

       ☺       ♀☻   PAutoImplementedProperties, Version=1.0.0.0, Cul

ture=neutral, PublicKeyToken=null♣☺   'Properties.AutoImplemented.Jord

evMember♦   §<Name>k__BackingField¶<Job>k__BackingField▬<Email>k__Back

ingField∟<DateOfBirth>k__BackingField☺☺☺ ♪☻   ♠♥   ♣Ammar♠♦   ◄Softwar

e Engineer♠♣   ►Ammar@jordev.net       

 

As I mentioned before the binary serialization persist all the private and public members of the object, we can notice here the underlying auto generated backing fields names into the content of the deserialized file.

Here's below the JordevMember class with the old pattern of implementing the properties:

/// <summary>

/// This is the classical class of JordevMember using trivial way of implementing properties.

/// </summary>

public class JordevMember

{

 

    private string _name;

    private string _job;

    private string _email;

    private DateTime _dateofbirth;

 

    public string Name

    {

        get

        {

            return _name;

        }

        set

        {

            _name = value;

        }

    }

 

    public string Job

    {

        get

        {

            return _job;

        }

        set

        {

            _job = value;

        }

    }

 

    public string Email

    {

        get

        {

            return _email;

        }

        set

        {

            _email = value;

        }

    }

 

    public DateTime DateOfBirth

    {

        get

        {

            return _dateofbirth;

        }

        set

        {

            _dateofbirth = value;

        }

    }

 

}

 

If we try to use the classic version of properties with the Pre-Serialized files we will see no results.

As we see in the previous samples, it's not recommended to use the automatic properties when the Binary serialization is required.

 

Cheers,

Posted: Friday, September 07, 2007 1:07 AM by moh.kanaan

Comments

No Comments

Anonymous comments are disabled