我正在尝试将给定的XML文件反序列化为对象结构。
这是XML:
<StaticData>
<Configuration>
<SqlCmdParameters />
<Tables>
<Table Schema="dbo" Name="table1">
<Columns>
<Column Name="tab1col1" IsPrimaryKey="false" />
<Column Name="tab1col2" IsPrimaryKey="false" />
</Columns>
</Table>
<Table Schema="dbo" Name="table2">
<Columns>
<Column Name="tab2col1" IsPrimaryKey="false" />
<Column Name="tab2col2" IsPrimaryKey="false" />
</Columns>
</Table>
</Tables>
</Configuration>
<TableDataItems>
<TableData Schema="dbo" Name="table1">
<RowData tab1col1="11" tab1col2="text1" tab1col3="anotherText1" />
<RowData tab1col1="12" tab1col2="text2" tab1col3="anotherText2"/>
<RowData tab1col1="13" tab1col2="text3" tab1col3="anotherText3"/>
</TableData>
<TableData Schema="dbo" Name="table2">
<RowData tab2col1="22" tab2col2="text1" />
<RowData tab2col1="23" tab2col2="text1" />
<RowData tab2col1="24" tab2col2="text1" />
</TableData>
</TableDataItems>
</StaticData>
我要填写的课程是:
[XmlRoot("StaticData")]
public class StaticData
{
[XmlElement("Configuration")]
public Configuration Configuration { get; set; }
[XmlElement("TableDataItems")]
public TableDataItems TableDataItems { get; set; }
}
public class Configuration
{
[XmlElement("Tables")]
public List<Table> Tables { get; set; }
[XmlElement("SqlCmdParameters")]
public List<SqlCommandParameter> SqlCommandParameters { get; set; }
}
public class TableDataItems
{
[XmlElement("TableData")]
public List<Table> TableDatas { get; set; }
}
public class Table
{
[XmlAttribute("Name")]
public string TableName { get; set; }
[XmlAttribute("Schema")]
public string SchemaName { get; set; }
[XmlElement("Columns")]
public List<Column> Columns { get; set; }
[XmlElement("RowData")]
public List<Row> Rows { get; set; }
public Table()
{
Columns = new List<Column>();
Rows = new List<Row>();
}
}
public class Column
{
[XmlAttribute("Name")]
public string Name { get; set; }
[XmlAttribute("IsPrimaryKey")]
public bool IsPrimaryKey { get; set; }
}
public class Row
{
public Row()
{
RowData = new Dictionary<string, string>();
}
???What Attribute should I put here???
public Dictionary<string, string> RowData { get; set; }
}
所以,一切正常,直到我到达应该将所有属性填充到字典中的位置为止。
到目前为止,这是我反序列化XML的方式:
public void CreateObjectStructureFromXml()
{
using (TextReader textReader = new StringReader(XmlDocument.ToString()))
{
XmlSerializer serializer = new XmlSerializer(typeof(StaticData));
StaticData = (StaticData) serializer.Deserialize(textReader);
}
}
我一旦获得Row元素,就会得到一个异常。
有人可以指出我的错误之处或应该怎么做吗? XML RowData可以带有可变数量的属性。这些属性是数据库表的内容。
非常感谢
答案 0 :(得分:0)
尝试xml linq:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Linq;
namespace ConsoleApplication1
{
class Program
{
const string FILENAME = @"c:\temp\test.xml";
static void Main(string[] args)
{
XDocument doc = XDocument.Load(FILENAME);
Table.tables = doc.Descendants("Table").Select(x => new Table() {
SchemaName = (string)x.Attribute("Schema"),
TableName = (string)x.Attribute("Name"),
Columns = x.Descendants("Column").Select(y => new Column()
{
Name = (string)y.Attribute("Name"),
IsPrimaryKey = (Boolean)y.Attribute("IsPrimaryKey")
}).ToList()
}).ToList();
Dictionary<string, XElement> tableData = doc.Descendants("TableData")
.GroupBy(x => (string)x.Attribute("Name"), y => y)
.ToDictionary(x => x.Key, y => y.FirstOrDefault());
foreach(Table table in Table.tables)
{
XElement xTable = tableData[table.TableName];
table.SchemaName = (string)xTable.Attribute("Schema");
table.Rows = xTable.Elements("RowData").Select(x => new Row() {
RowData = x.Attributes()
.GroupBy(y => y.Name.LocalName, z => (string)z)
.ToDictionary(y => y.Key, z => z.FirstOrDefault())
}).ToList();
}
}
}
public class Table
{
public static List<Table> tables = new List<Table>();
public string TableName { get; set; }
public string SchemaName { get; set; }
public List<Column> Columns { get; set; }
public List<Row> Rows { get; set; }
public Table()
{
Columns = new List<Column>();
Rows = new List<Row>();
}
}
public class Column
{
public string Name { get; set; }
public bool IsPrimaryKey { get; set; }
}
public class Row
{
public Dictionary<string, string> RowData { get; set; }
}
}