Показаны сообщения с ярлыком xml. Показать все сообщения
Показаны сообщения с ярлыком xml. Показать все сообщения

среда, 3 ноября 2010 г.

Why do I have to XmlInclude derived classes in order to serialize?

I have a shallow, but wide class heirarchy.  I have one base class with several derived classes.
During serialization, I pass a reference to the XmlSerializer.  The reference never points to the base class; it points to one of the derived classes.

So when I attempt to serialize

public class Base

public class Derived1 : Base
public class Derived2 : Base
public class DerivedN : Base


XmlSerializer ser = new XmlSerializer(typeof(Base));
StreamWriter writer = new StreamWriter(sFilename);
ser.Serialize(writer, DerivedClassFactory.CreateRandom() );
//DerivedClassFactory can create any of the derived classes..



On this last line, the execution fails with a run time error:
"The type LibraryName.Classname was not expected. Use the XmlInclude or SoapInclude attribute to specify types that are not known statically."

I took this suggestion and added
    [System.Xml.Serialization.XmlInclude(typeof(Derived1))]
    [System.Xml.Serialization.XmlInclude(typeof(Derived2))]
    [System.Xml.Serialization.XmlInclude(typeof(DerivedN))]

to the Base class definition.  The code now executes fine.  The problem is, what if I do not own the base class definition?  What if I do not have access to the base class definition?  Isn't there a better way to do this????




You can achieve the same by using different XmlSerializer ctor, the one that takes an univerce of “known” types:   public XmlSerializer(Type type, Type[] extraTypes){..}

In your case: new XmlSerializer(typeof(Base), new Type[] { typeof(Derived1), ..});

вторник, 6 апреля 2010 г.

How to serialize an object to XML by using Visual C#

Serialzation


Now here's the cool part. This is how serialization works:

ShoppingList myList = new ShoppingList();
myList.AddItem( new Item( "eggs",1.49 ) );
myList.AddItem( new Item( "ground beef",3.69 ) );
myList.AddItem( new Item( "bread",0.89 ) );


// Serialization
XmlSerializer s = new XmlSerializer( typeof( ShoppingList ) );
TextWriter w = new StreamWriter( @"c:\list.xml" );
s.Serialize( w, myList );
w.Close();

// Deserialization
ShoppingList newList;
TextReader r = new StreamReader( "list.xml" );
newList = (ShoppingList)s.Deserialize( r );
r.Close();

The first chunk of code is simply creating an instance of the ShoppingList class and populating it. After that, we have the serialization part. Here is where the object gets converted into XML. As you can see, all it requires is the use of the XmlSerializer class which is set to serialize anything of type ShoppingList (look at the constructor). The serializer does its work when the Serialize method is called and will output XML to any stream. In this case, we have it output to a file.
Next there is the deserialization part. Here we use the same serializer (since it's set to the right type) and we read in an XML file and the Deserialize method will create the appropriate ShoppingList class object. This code sample shows serialization from a file, but you could just as easily do it from an http stream.