Blog Archives

XML (part 1, basics), file IO

The last days were tough. Writing posts requires a lot of time. Explaining some basic know-how will give me some recreation today.

I will concentrate on the C# parts. There will be no explanations about XML, which is well documented across the internet.

XML stands for eXtensible Markup Language. XML is a versatile and flexible data structure. It is easy to read, learn and understand. The downside is the amount of bytes it needs. You can use XML to transport and/or store data, but it quickly becomes quite inefficient when a lot of datasets are involved.

XML is a well established industry standard. So there is no way around it, you have to know at least something about it.

Here is an XML file that we will use in the loading example:

<?xml version="1.0" encoding="UTF-8"?>
<!-- XML EXAMPLE -->
<Walmart>
	<food>
		<name>Banana</name>
		<price>1.99</price>
		<description>Mexican delicious</description>
	</food>
	<food>
		<name>Rice</name>
		<price>0.79</price>
		<description>the best you can get</description>
	</food>
	<food>
		<name>Cornflakes</name>
		<price>3.85</price>
		<description>buy some milk</description>
	</food>
	<food>
		<name>Milk</name>
		<price>1.43</price>
		<description>from happy cows</description>
	</food>
  <electronic>
    <name>Kindle fire</name>
    <price>100</price>
    <description>Amazon loves you</description>
    <somethingElse>the perfect Xmas gift for your kids</somethingElse>
  </electronic>
	<food>
		<name>baked beans</name>
		<price>1.35</price>
		<description>very British</description>
	</food>
</Walmart>

Paste the XML structure into a text editor and save it as an XML file (“Walmart.xml”) onto your desktop.
The following class will be used to store datasets in memory.

 public class WmItem {
    public readonly string name;
    public readonly double price;
    public readonly string description;

    public WmItem(string xName, double xPrice, string xDescription) {
        name = xName;
        price = xPrice;
        description = xDescription;
    } // constructor

    public override string ToString() {
        return name.PadRight(12) + price.ToString("#,##0.00").PadLeft(8) + " " + description;
    } //
} // class

Loading XML files is easy. Processing files takes a bit longer. The centerpiece generally is the parsing algorithm.
There is a field called “somethingElse” in the XML file. It does not cause any trouble. The code simply disregards it. I added it to demonstrate the “eXtensible” in “eXtensible Markup Language”.

public static void LoadXml() {
    string lDesktopPath = Environment.GetFolderPath(Environment.SpecialFolder.DesktopDirectory) + @"\";
    string lFile = lDesktopPath + "Walmart.xml";

    XDocument lXDocument = XDocument.Load(lFile);

    // food (using WmItem)
    WmItem[] lFood = (from lData in lXDocument.Descendants("Walmart").Descendants("food")
                        select new WmItem(
                            lData.Element("name").Value,
                            double.Parse(lData.Element("price").Value),
                            lData.Element("description").Value)
                ).ToArray();

    foreach (WmItem lItem in lFood) Console.WriteLine(lItem);

    Console.WriteLine();

    // electronic (quick and dirty, using var)
    var lElectronic = from lData in lXDocument.Descendants("Walmart").Descendants("electronic")
                        select lData;

    foreach (var lItem in lElectronic) {
        Console.WriteLine(lItem);
        Console.WriteLine();
        Console.WriteLine(lItem.Element("name").Value);
        Console.WriteLine(lItem.Element("price").Value);
        Console.WriteLine(lItem.Element("description").Value);
    }

    Console.ReadLine();
} //

example output:
Banana          1.99 Mexican delicious
Rice            0.79 the best you can get
Cornflakes      3.85 buy some milk
Milk            1.43 from happy cows
baked beans     1.35 very British

<electronic>
  <name>Kindle fire</name>
  <price>100</price>
  <description>Amazon loves you</description>
  <somethingElse>the perfect Xmas gift for your kids</somethingElse>
</electronic>

Kindle fire
100
Amazon loves you

Saving XML is also straight forward. I added a comment and attributes for demonstration purposes. The program generates and saves the XML file “Genesis.xml” on your desktop.

public static void SaveXml() {
    string lDesktopPath = Environment.GetFolderPath(Environment.SpecialFolder.DesktopDirectory) + @"\";
    string lFile = lDesktopPath + "Genesis.xml";

    WmItem[] lMetals = { 
                            new WmItem("Lead", 1.0, "here we go"),
                            new WmItem("Silver", 2.0, "cutlery"),
                            new WmItem("Gold", 3.0, "wife's best friend"),
                            new WmItem("Platinum", 4.0, "posh") 
                        };
            
    XDocument lXDocument = new XDocument();
    lXDocument.Declaration = new XDeclaration("1.0", "utf-8", "yes");
    lXDocument.Add(new XComment("copyfight by Bastian M.K. Ohta"));
            
    XElement lLME = new XElement("London_Metal_Exchange", new XAttribute("attribute1", "buy here"), new XAttribute("AreYouSure", "yes"));
    lXDocument.Add(lLME);

    foreach (WmItem lMetal in lMetals) {
        XElement lGroup = new XElement("metal");
        lGroup.Add(new XElement("name", lMetal.name));
        lGroup.Add(new XElement("price", lMetal.price));
        lGroup.Add(new XElement("description", lMetal.description));
        lLME.Add(lGroup);
    }

    lXDocument.Save(lFile);

    //Console.ReadLine();
} //