将Xml转换为DataTable

13

我有一个XML文件,我想将其插入Datatable中。 XML文件的格式如下:

<userid ID="37729">
  <TestId ID="84" TimeRemaining="60" />
  <QuestId ID="1">
    <Answer1>
    </Answer1>
    <Answer2>B</Answer2>
    <Answer3>
    </Answer3>
    <Answer4>
    </Answer4>
  </QuestId>
</userid>

现在我想将其插入到如下的数据表中:

Question Id     Answer1      Answer2        Answer3        Answer4
1                 A                                         D

2                             B              C     

3                                            C                     

有人能帮助我实现这个吗。


请适当格式化您需要插入 DataTable 中的数据,这样更容易理解。 - Hasan Fahim
1
你需要使用 DataTable 的特定原因吗?你可以定义一个可序列化的类,并将其反序列化为对象,这样做可能更容易,并且以这种形式使用它可能更有用。 - Joe Enos
@Joe Enos,是的,就像 @ColinE 建议的那样,您可以使用 Linq-to-XML。 - DOK
@Joe:没有特定的要求,只是想将XML文件以表格格式存储,就像上面的例子一样。 - Vijjendra
5个回答

17

我会首先创建一个包含所需列的 DataTable,然后通过 Linq-to-XML 填充它。

你可以使用 Select 查询来创建代表每一行的对象,然后使用标准的方法为每个项目创建 DataRow...

class Quest
{
    public string Answer1;
    public string Answer2;
    public string Answer3;
    public string Answer4;
}

public static void Main()
{
    var doc = XDocument.Load("filename.xml");

    var rows = doc.Descendants("QuestId").Select(el => new Quest
    {
        Answer1 = el.Element("Answer1").Value,
        Answer2 = el.Element("Answer2").Value,
        Answer3 = el.Element("Answer3").Value,
        Answer4 = el.Element("Answer4").Value,
    });

    // iterate over the rows and add to DataTable ...

}

7
但我想知道为什么在 new() 后面出现了 type expected 的错误提示。 - user1590636
@user1590636,因为这段代码无法编译。我已将所需信息编辑到答案中。另一个小错误是重载XDocument.Load(yourxmlstring)期望字符串是文件的Uri,而不是字面上的XML - 将参数名称更改为“filename.xml”。当您需要直接从字符串加载时,请使用MemoryStream。 - Cee McSharpface
如果您不知道元素的名称怎么办? - Demodave

15
DataSet ds = new DataSet();
ds.ReadXml(fileNamePath);

6
提供的XML格式是否适合ReadXml方法?你确定吗? - ColinE

2

你确定提供的XML格式适合ReadXml吗? - ColinE
@ColinE,我不确定,特别是问题的编辑。通过运行代码很容易找出答案。如果这种方法可行,就可以避免创建列和选择语句。如果数据源可以适应ReadXml方法,那将节省大量的工作。 - DOK

1

您可以使用此代码(建议)

 MemoryStream objMS = new MemoryStream();
 DataTable oDT = new DataTable();//Your DataTable which you want to convert
 oDT.WriteXml(objMS);
 objMS.Position = 0;
 XPathDocument result = new XPathDocument(objMS);

这是另一种方式,但首选是第一个示例。

StringWriter objSW = new StringWriter();
DataTable oDt = new DataTable();//Your DataTable which you want to convert
oDt.WriteXml(objSW);
string result = objSW.ToString();

3
你将要插入到 DataTable 中的 XML 在哪里?请先阅读问题。 - nZeus

-2
也许这篇文章有点旧了,但是上面的大多数答案都不能满足我的需求。所以我写了一小段代码来解决这个问题。
这个代码可以接受至少有三层级别的任何XML(就像这个示例)。
<XmlData>
    <XmlRow>
        <XmlField1>Data 1</XmlField1>  
        <XmlField2>Data 2</XmlField2>  
        <XmlField3>Data 3</XmlField3>  
        .......
    </XmlRow>
</XmlData>

public static class XmlParser
{
    /// <summary>
    /// Converts XML string to DataTable
    /// </summary>
    /// <param name="Name">DataTable name</param>
    /// <param name="XMLString">XML string</param>
    /// <returns></returns>
    public static DataTable BuildDataTableFromXml(string Name, string XMLString)
    {
        XmlDocument doc = new XmlDocument();
        doc.Load(new StringReader(XMLString));
        DataTable Dt = new DataTable(Name);
        try
        {

            XmlNode NodoEstructura = doc.FirstChild.FirstChild;
            //  Table structure (columns definition) 
            foreach (XmlNode columna in NodoEstructura.ChildNodes)
            {
                Dt.Columns.Add(columna.Name, typeof(String));
            }

            XmlNode Filas = doc.FirstChild;
            //  Data Rows 
            foreach (XmlNode Fila in Filas.ChildNodes)
            {
                List<string> Valores = new List<string>();
                foreach (XmlNode Columna in Fila.ChildNodes)
                {
                    Valores.Add(Columna.InnerText);
                }
                Dt.Rows.Add(Valores.ToArray());
            }
        } catch(Exception)
        {

        }

        return Dt;
    }
}

这解决了我的问题


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接