views:

1206

answers:

4

Using C#...I have a small app that creates objects from a class, and adds them to an object collection and it does some UI stuff along the way to display certain values from the currently selected object in the collection (Using WPF UI). So I want to add the ability to let the user save his object collection to a file, so they can load it back the next time they run the app.

I'm guessing XML is an obvious way to go, but I know nothing about how to do it. So, how do you export or dump a collection of objects to an xml file, and then, perhaps more importantly, how would I then read that XML file back into my app to re-create the collection?

Here is a screenshot of the app

A: 

System.Runtime.Serialization is your friend here, if you decide to go for XML.

In one of my test apps, I sometimes need to be able to serialise an object as XML so I can look at it all offline. Here's the snippet I use (not optimised in any way, just quickly knocked together one day, and it has worked as I needed it).

public static string ObjectToXml<T>(T objectToSerialise)
{
    StringWriter Output = new StringWriter(new StringBuilder());
    XmlSerializer xs = new XmlSerializer(objectToSerialise.GetType());
    XmlSerializerNamespaces ns = new XmlSerializerNamespaces();
    ns.Add("MyNs", "http://www.someXmlNamespace/namespace1"); // add as many or few as you need
    xs.Serialize(Output, objectToSerialise, ns);
    return Output.ToString();
}

After that, it's trivial to squirt the data out to a file.

Notes :
I needed to be able to get the XML content as a string so I could persist it one of several ways. Building a method to go direct to disk would be easy too, if that's what you need.
Although this works for me, you may need to tweak to meet your own needs.

ZombieSheep
A: 

There are a ton of topics on StackOverflow about XML Serialization, including a few excellent posts regarding some hidden gotchyas:

Saving Data Structures using Serialization

Serialization Gotchyas

Matt Jordan
+1  A: 

XML Serialization is OK and good for many situations, but the output will be a little bulky due to XML inherent overhead. In this situation where the file's contents don't need to be human readable, so this opens up other options.

JSON serialization will help keep the file size down. JavaScriptSerializer can be found in System.Web.Script.Serialization (System.Web.Extensions.dll).

In the example below I have a Typed generic list of ConfigurationItem. Configuration item is like any other class but the properties should be public for them to be serialized.

var strFileData = System.IO.File.ReadAllText("FileName.data");
var jss = new JavaScriptSerializer();
var objItemsList = jss.Deserialize<List<ConfigurationItem>>(strFileData);
// {insert code here tomanipulate object "objItemsList"}
var strNewData = jss.Serialize(objItemsList);
System.IO.File.WriteAllText("FileName.data", strNewData);
A: 

The problem with Serialisation to XML is that if your class being serialised changes (new property), then the xml cannot be used to recreate the instance of that class.

If the class is fairly simple (or even if it is not) you could do it manually:

XmlDocument doc = new XmlDocument();
XmlNode root = doc.CreateNode(XmlNodeType.Element,"root")
doc.AppendChild(root)
XmlNode newPage = doc.CreateNode(XmlNodeType.Element,"pattern")
root.AppendChild(newPage)
newPage.Attributes.Append(doc.CreateAttribute("Name",pattern.Name)
foreach (Hole h in pattern.Holes)
{
  XmlNode hole = doc.CreateNode(XmlNodeType.Element,"hole")
  hole.Attributes.Append(doc.CreateAttribute("XCoord",h.Xcoord)
  hole.Attributes.Append(doc.CreateAttribute("YCoord",h.Ycoord)
  newPage.AppendChild(hole)
}
// etc
doc.Save("output.xml")

This code is rough, but it would generate something like:

<root>
  <pattern name="Pattern1">
    <hole XCoord="100" YCoord="50" />
  </pattern>
</root>
benPearce