New versions vs. serialization

  • Thread starter Thread starter Guest
  • Start date Start date
G

Guest

Hi,

I'm writing a program which is, and will continue to be, constantly extended
with functionality that require information. Until now the source of this
information has been found and modified using notepad in a txt file that was
parsed into fields in objects. (This solution because this was the format
that an older fortran program was using and we needed to do it in this way in
a transition period). Now I would like be able to save from the program and
wish to switch to object serialization, but I'm concerned about backward
compatibility if my classes that are serialized on disk is constantly
extended.

If I extend a class with a field and try to desirialize this class from a
source which did not have the field, I guess I'll get an exception, Right?.
Are there any attributes that can provide some kind of default values for
fields or indicate that it is 'OK!' that the field wasn't found.

Must a class match exactly the fields.

Alternatively I would use xml and write my own serialization and
deserialization methods. Rather cumbersome but maybe necessary if I want this
degree of freedom.

Another way could be to keep the old framework and then parse information
from this old framework to the new one - like when you open a word 97
document in word 2003.

Please comment.

best regards Jesper, Denmark.
 
Did you ever find a solution to this problem? I have a similar issue and am
looking for a solution.
 
Don't know if this solves your problem, but you could use one of the classes
that implements IDictionary interface, and is serializable. The keys would
be strings that represented the field named. The values would be objects
that you would have to cast to the correct type when you pulled them from
the dictionary. If a field was not found it could be added with a default
value (and saved when the dictionary was written out). Accessing a field
through a dictionary in this way is rather expensive in CPU time, though.

If you did not want to pay the cost to access the "fields" from the
dictionary, each time they are needed, you could make a constructor for your
extensible class(es). The constructor would read the serialized dictionary
from the file. For each field in the class, it would attempt to fetch it
from the dictionary; if found it would assign it from the dictionary to the
field in the object. If not found, it would initialize it appropriately.
After construction, access to the fields is just from the object.

When your extensible class changes, you have to recompile the new class
definition and change the constructor. However, the old serialized
dictionary will be read and the new version of the class initialized with
the existing fields from the dictionary. The new fields would be defaulted
by the new constructor code you wrote, when/if they were not found in the
dictionary.

Some part of your application would write out the serializable dictionary,
after updating the key/values in the dictionary from the object you were
using.

This is about the same as saving XML and parsing it to build an object of
"extensible class", but use of the dictionary saves you the trouble of
writing parsing logic.

You could have separate dictionaries and files for each extensible class,
but it might be easier to have one serializable dictionary. You could
easily qualify the field names (strings) with the class, as in "foo.in",
"bar.in", and use them to build the "bar" and "foo" objects appropriately.
 
This is the best solution I've seen proposed yet. It appears at least a half
a dozen other people have a question similar to mine but I've not yet seen a
solution proposed to any of their posts. As for the proposal, it will
require time to re-code it this way, but I think it would work. Thanks for
the idea.
 
Hi steeve

I am facing the same problem. Kindly send me sample code or workarounds for
this problem.

Thanks
 
Hi steeve

I am facing the same problem. Kindly send me sample code or workarounds for
this problem.

Thanks
 
Hi steeve

I am facing the same problem. Kindly send me sample code or workarounds for
this problem.

Thanks
 
Hi steeve

I am facing the same problem. Kindly send me sample code or workarounds for
this problem.

Thanks
 
Hi. I was out on vacation so this may be coming to you too late. What I did
is below.

I created a dictionary class that saves any component of type "Object". The
key for each object is unique. The value is of type Object.

I followed a convention of having the namespace, module and field as the
unique name.

Ex. private readonly string strKey4 =
"TestingPowerCycle.TestingPowerCycling.SecondsBeforePowerCycle";

The method to save the data is below.
/// <summary>
/// Save the data to the dictionary.
/// </summary>
/// <param name="mod">DictionaryObjects.MyObjectDictionary where data is
stored.</param>
public override void SaveData(ref DictionaryObjects.MyObjectDictionary mod)
{
mod.Add(this.strKey4, this.SecondsBeforePowerCycle.ToString());
}

The method to retrieve data is below.

/// <summary>
/// Retrieve data from the dictionary.
/// </summary>
/// <param name="mod">DictionaryObjects.MyObjectDictionary where data was
stored.</param>
public override void RetrieveData(DictionaryObjects.MyObjectDictionary mod)
{
if (mod.Contains(this.strKey4))
this.SecondsBeforePowerCycle = Convert.ToInt32((string)mod[this.strKey4],
10);
}

When streaming the data to the disk I would call similar routines for each
class, save the data to the dictionary, then stream the dictionary to the
disk. You just need to remember that the key must be unique.

Hope this helps.
 
Steeve,

But this doesnt work for the files already serialized. I want to deserialize
a file that was already saved. Anyway i got up with a a solution. I used
Iserializable interface and it worked.

Thanks

Steve Teeples said:
Hi. I was out on vacation so this may be coming to you too late. What I did
is below.

I created a dictionary class that saves any component of type "Object". The
key for each object is unique. The value is of type Object.

I followed a convention of having the namespace, module and field as the
unique name.

Ex. private readonly string strKey4 =
"TestingPowerCycle.TestingPowerCycling.SecondsBeforePowerCycle";

The method to save the data is below.
/// <summary>
/// Save the data to the dictionary.
/// </summary>
/// <param name="mod">DictionaryObjects.MyObjectDictionary where data is
stored.</param>
public override void SaveData(ref DictionaryObjects.MyObjectDictionary mod)
{
mod.Add(this.strKey4, this.SecondsBeforePowerCycle.ToString());
}

The method to retrieve data is below.

/// <summary>
/// Retrieve data from the dictionary.
/// </summary>
/// <param name="mod">DictionaryObjects.MyObjectDictionary where data was
stored.</param>
public override void RetrieveData(DictionaryObjects.MyObjectDictionary mod)
{
if (mod.Contains(this.strKey4))
this.SecondsBeforePowerCycle = Convert.ToInt32((string)mod[this.strKey4],
10);
}

When streaming the data to the disk I would call similar routines for each
class, save the data to the dictionary, then stream the dictionary to the
disk. You just need to remember that the key must be unique.

Hope this helps.
--
Steve


Rohith said:
Hi steeve

I am facing the same problem. Kindly send me sample code or workarounds for
this problem.

Thanks
 
Back
Top