Deserialising xml and Inheritance

  • Thread starter Johannes Elsinghorst
  • Start date
J

Johannes Elsinghorst

Hello,
I have a class "Version" and another two classes "SpezielleVersion1"
and "SpezielleVersion2", which inherit from "Version".
When i deserialize a xml-Instance of "SpezielleVersion1" like this:
XmlSerializer xs = new XmlSerializer(typeof(SpezielleVersion1));
XmlTextReader reader = new XmlTextReader(input);
return (SpezielleVersion1)xs.Deserialize(reader);

i get a proper object in return. But sometimes i dont want to
distinguish between
"SpezielleVersion1" and "SpezielleVersion2", instead i want to
deserialize them as a"Version":
XmlSerializer xs = new XmlSerializer(typeof(Version));
XmlTextReader reader = new XmlTextReader(input);
return (Version)xs.Deserialize(reader);

For that i annotated the "Version" class with
[XmlInclude(typeof(SpezielleVersion1),XmlInclude(typeof(SpezielleVersion2)]
Unfortunately the deserializer quits with an
IllegalArgumentException("<SpeziellVersion1 xmlns='http://...'> wasnt
expectedt.) when it reads "<zg:SpeziellVersion1... >" in the xml-file.

Does anybody have a clue why it does that?
thanks, Johannes Elsinghorst
 
J

John Saunders [MVP]

Johannes Elsinghorst said:
Hello,
I have a class "Version" and another two classes "SpezielleVersion1"
and "SpezielleVersion2", which inherit from "Version".
When i deserialize a xml-Instance of "SpezielleVersion1" like this:
XmlSerializer xs = new XmlSerializer(typeof(SpezielleVersion1));
XmlTextReader reader = new XmlTextReader(input);
return (SpezielleVersion1)xs.Deserialize(reader);

i get a proper object in return. But sometimes i dont want to
distinguish between
"SpezielleVersion1" and "SpezielleVersion2", instead i want to
deserialize them as a"Version":
XmlSerializer xs = new XmlSerializer(typeof(Version));
XmlTextReader reader = new XmlTextReader(input);
return (Version)xs.Deserialize(reader);

For that i annotated the "Version" class with
[XmlInclude(typeof(SpezielleVersion1),XmlInclude(typeof(SpezielleVersion2)]
Unfortunately the deserializer quits with an
IllegalArgumentException("<SpeziellVersion1 xmlns='http://...'> wasnt
expectedt.) when it reads "<zg:SpeziellVersion1... >" in the xml-file.

Does anybody have a clue why it does that?
thanks, Johannes Elsinghorst

Johannes, I have a question just to be clear. Does the failing XML file
succeed if you use "XmlSerializer xs = new
XmlSerializer(typeof(SpezielleVersion1))"?

Do you have the XML namespaces correct? You didn't show that in your post.
 
J

Johannes Elsinghorst

Hi John,
thanks for your reply.
Johannes, I have a question just to be clear. Does the failing XML file
succeed if you use "XmlSerializer xs = new
XmlSerializer(typeof(SpezielleVersion1))"?
Yes, i get an object with all the properties of "SpezielleVersion1"
and "Version", so inheritance works 'downwards'.
Do you have the XML namespaces correct? You didn't show that in your post.
--
Yes, the namespace conforms with the one specified in the xsd.

regards, Johannes.
 
F

Frans Bouma [C# MVP]

Johannes said:
Hello,
I have a class "Version" and another two classes "SpezielleVersion1"
and "SpezielleVersion2", which inherit from "Version".
When i deserialize a xml-Instance of "SpezielleVersion1" like this:
XmlSerializer xs = new XmlSerializer(typeof(SpezielleVersion1));
XmlTextReader reader = new XmlTextReader(input);
return (SpezielleVersion1)xs.Deserialize(reader);

i get a proper object in return. But sometimes i dont want to
distinguish between
"SpezielleVersion1" and "SpezielleVersion2", instead i want to
deserialize them as a"Version":
XmlSerializer xs = new XmlSerializer(typeof(Version));
XmlTextReader reader = new XmlTextReader(input);
return (Version)xs.Deserialize(reader);

For that i annotated the "Version" class with
[XmlInclude(typeof(SpezielleVersion1),XmlInclude(typeof(SpezielleVersi
on2)] Unfortunately the deserializer quits with an
IllegalArgumentException("<SpeziellVersion1 xmlns='http://...'> wasnt
expectedt.) when it reads "<zg:SpeziellVersion1... >" in the xml-file.

Does anybody have a clue why it does that?
thanks, Johannes Elsinghorst

The XmlSerializer generates C# code under the hood to perform the
serialization/deserialization. As you specified 'Version' as the type,
it will create code which creates a new instance of Version (how else
would it know what to create to store the data in?) and as you want to
have a different type back, this won't work.

Only exact type matches work with xml serialization as xml
serialization is about data, not about objects. So the data doesn't
represent a type, it represents the data in xml format. that it fits
inside an object of type X or Y isn't important.

FB

--
------------------------------------------------------------------------
Lead developer of LLBLGen Pro, the productive O/R mapper for .NET
LLBLGen Pro website: http://www.llblgen.com
My .NET blog: http://weblogs.asp.net/fbouma
Microsoft MVP (C#)
------------------------------------------------------------------------
 
J

Johannes Elsinghorst

What is the XMLInclude-Annotation used for, if serialization doesn't
work this way?

regards, Johannes.
 
J

JS

I had the same problems using serialization a couple of years back and
decided that serialization for saving/loading data was not the right
technology to use (in my case at least). I ended up writing my own
'serialize/deserialize' which could deserialize into an existing
object. The main negative with my solution is that I have to write
the serialize/deserialize code for each object. I wish .Net had
supported deserializing into an existing object. It would have saved
me a lot of work.
 
R

Rohit

What is the XMLInclude-Annotation used for, if serialization doesn't
work this way?

regards, Johannes.







- Show quoted text -

XMLInclude annotation used to include the objects which have
association to the current object. Means if we have a refernce of some
other object which is also a serializabe object then the serialization/
deserialization will include that also.

Serialization/Deserialization is related to data not to an object that
is why inheritanceis not taken care of but the association is taken
care.
 
R

Rohit

I had the same problems using serialization a couple of years back and
decided that serialization for saving/loading data was not the right
technology to use (in my case at least). I ended up writing my own
'serialize/deserialize' which could deserialize into an existing
object. The main negative with my solution is that I have to write
the serialize/deserialize code for each object. I wish .Net had
supported deserializing into an existing object. It would have saved
me a lot of work.
 
R

Rohit

I had the same problems using serialization a couple of years back and
decided that serialization for saving/loading data was not the right
technology to use (in my case at least). I ended up writing my own
'serialize/deserialize' which could deserialize into an existing
object. The main negative with my solution is that I have to write
the serialize/deserialize code for each object. I wish .Net had
supported deserializing into an existing object. It would have saved
me a lot of work.

The approach you have taken in that also if you design it properly,
you need not do lot of coding.

You can create a abstract base class which has one methods for
deserialization and another for serialization and using reflection you
can get the public properties and do the serialization/
deserialization. Now you need to just inherit this class for your
object classes.Now you need not write the code for serialization/
deserialization in every class.

-Regards
Rohit
 
J

Johannes Elsinghorst

Our approach is somewhat different, ew actually dont do serialization.
We first create the schemas and xml
and only need to deserialize them as they are config-files.
So as i see it there is no way to tell the Deserializer about the
inheritance, i have to know of what exact type my xml is
in order to deserialize it?

regards, Johannes.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top