Reputation: 503
Hoping someone can point me in the right direction with this.
I am trying to iterate through an xml file and get each "table" in the xml file, and get each child rows etc.
I am able to get the rows that are not child rows etc just fine.
Here is an example of the xml structure.
<items>
<item>
<id>1</id>
<row1>abc</row1>
<row2>abc</row2>
<needthis>
<first>John</first>
<last>John</last>
</needthis>
</item>
</items>
This is what I am currently using.
foreach (DataTable table in ds.Tables)
{
foreach (DataRow row in table.Rows)
{
foreach (DataColumn column in table.Columns)
{
object item = row["id"];
object item2 = row["row1"];
//Just to see what is returning
System.Windows.Forms.MessageBox.Show(item.ToString());
System.Windows.Forms.MessageBox.Show(item2.ToString());
}
}
}
What would I need to get the first row and last row of needthis table?
Upvotes: 1
Views: 6247
Reputation: 52655
Personally I like Linq to XML for this kind of thing.
//Probably want to use Load if you're using a file
XDocument xDoc =
XDocument.Parse (@"
<items>
<item>
<id>1</id>
<row1>abc</row1>
<row2>abc</row2>
<needthis>
<first>John</first>
<last>John</last>
</needthis>
</item>
</items>");
var items = from item in xDoc.Descendants("item")
from needThis in item.Descendants("needthis")
select new
{ Id = item.Element("id").Value,
Row1 = item.Element("row1").Value,
first = needThis.Element("first").Value,
last = needThis.Element("last").Value
};
foreach (var item in items)
{
Console.WriteLine(item.Id);
Console.WriteLine(item.Row1);
Console.WriteLine(item.first);
Console.WriteLine(item.last);
}
If for some reason you really needed to use datasets you will need to do the following
using(MemoryStream stream = new MemoryStream())
{
StreamWriter writer = new StreamWriter(stream);
writer.Write(@"
<items>
<item>
<id>1</id>
<row1>abc</row1>
<row2>abc</row2>
<needthis>
<first>John</first>
<last>John</last>
</needthis>
</item>
</items>");
writer.Flush();
stream.Position = 0;
DataSet ds = new DataSet();
ds.ReadXml(stream);
DataTable table = ds.Tables["item"];
foreach (DataRow row in table.Rows)
{
Console.WriteLine( row["id"] );
Console.WriteLine( row["row1"] );
var ChildRows = row.GetChildRows("item_needthis");
foreach(var ntRow in ChildRows)
{
Console.WriteLine( ntRow["first"]);
Console.WriteLine( ntRow["last"]);
}
}
}
You could also use Linq to Datasets
Upvotes: 2
Reputation: 13286
I would use the XElement
class instead of DataSets. Then you could read your file even with just this:
XElement root = XElement.Load(...); // or Parse(...)
return root.Elements("item").Select(c => new { id = c.Element("id").Value,
row1 = c.Element("row1").Value,
row2 = c.Element("row2").Value,
needthis = new { first = c.Element("needthis").Element("first").Value,
last = c.Element("needthis").Element("last").Value } });
Of course I haven't tested this, but you can see the point. It also doesn't have any error handling, and it could be more efficient, but again you can see the gist of how it works.
Upvotes: 1