Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

XML to IEnumerable<T>

Tags:

c#

xml

asp.net

linq

Is there a way to Take a given XML file and convert (preferably using C# Generics) it into a Concrete Ienumerable list of T where T is my concrete class

So for example I may have an XML file like

<fruits>
    <fruit>
        <id>1</id>
        <name>apple</name>
    </fruit>
    <fruit>
        <id>2</id>
        <name>orange</name>
    </fruit>
</fruits>

and I would like to see a list of a Fruit Objects

where it has properties like

public class Fruit : IFruit
{
    public string name;
    public int id;
}

I assume I'd need some kind of Mapping if I was to use generics, as I would like this to work for ideally the IFruit interface (not sure if thats possible)

Thanks in advance

like image 378
Mark H Avatar asked Sep 22 '09 14:09

Mark H


2 Answers

Given the following types:

public interface IFruit
{
    String name { get; set; }
    Int32 id { get; set; }
}

public class Fruit : IFruit
{
    public String name { get; set; }
    public Int32 id { get; set; }
}

I think that you could do something like this:

    static IEnumerable<T> GetSomeFruit<T>(String xml)
        where T : IFruit, new()
    {
        return XElement.Parse(xml)
            .Elements("fruit")
            .Select(f => new T {
                name = f.Element("name").Value,
                id = Int32.Parse(f.Element("id").Value)
            });
    }

Which you would call like this:

IEnumerable<Fruit> fruit = GetSomeFruit<Fruit>(yourXml);
like image 127
Andrew Hare Avatar answered Sep 28 '22 10:09

Andrew Hare


Here's a way to do it with serialization, if that's your thing:

using System;
using System.IO;
using System.Xml.Serialization;

public static class Test
{
    public static void Main(string[] args)
    {
        var fs = new FileStream("fruits.xml", FileMode.Open);
        var x = new XmlSerializer(typeof(Fruits));
        var fruits = (Fruits) x.Deserialize(fs);
        Console.WriteLine("{0} count: {1}", fruits.GetType().Name, fruits.fruits.Length);
        foreach(var fruit in fruits.fruits)
            Console.WriteLine("id: {0}, name: {1}", fruit.id, fruit.name);
    }
}

[XmlRoot("fruits")]
public class Fruits
{
    [XmlElement(ElementName="fruit")]
    public Fruit[] fruits;
}

public class Fruit
{
    public string name;
    public int id;
}
like image 42
brianary Avatar answered Sep 28 '22 08:09

brianary