简体   繁体   English

将 DataGridView 的内容添加到现有 XML 文件

[英]Add the contents of a DataGridView to an existing XML file

So I finally was able to create a XML and change it as I want but now I needed to add the contents of a DataGridView to it.所以我终于能够创建一个 XML 并根据需要更改它,但现在我需要向其中添加DataGridView的内容。 I thought that's quite easy as I saw the options to place it into a DataSet and use XmlWrite , but that was a mistake of me.我认为这很容易,因为我看到了将其放入DataSet并使用XmlWrite的选项,但这是我的错误。 Note that I'm still trying to learn C# so probably I make a silly mistake here.请注意,我仍在尝试学习 C#,所以我可能在这里犯了一个愚蠢的错误。 It is still not working maybe someone is willing to point me out what I am doing wrong?它仍然不起作用也许有人愿意指出我做错了什么?

I actually have two issues with this:我实际上有两个问题:

  1. It ForEach loop doesn't get the existing column namesForEach循环没有得到现有的列名

  2. It doesn't add the table and its contents to the XML file它不会将表及其内容添加到 XML 文件中

    private void CreateClientFile() { string filename;私人无效 CreateClientFile() { 字符串文件名; filename = Company + "_" + SiteName + ".xml";文件名=公司+“_”+站点名称+“.xml”;

     XmlDocument doc = new XmlDocument(); XmlElement root = doc.CreateElement("CompanyProfile"); doc.AppendChild(root); //Save document on Harddisk doc.Save(@"C:\Users\NLRAGIL\Documents\10 - VibroManager\" + filename); //Need to save first and than load again???? //Load document into program doc.Load(@"C:\Users\NLRAGIL\Documents\10 - VibroManager\" + filename); XmlNode main = doc.SelectSingleNode("CompanyProfile"); //Create Company name element XmlElement companyname = doc.CreateElement("CompanyName"); companyname.InnerText = CompanyName; main.AppendChild(companyname); //Create sitename element XmlElement sitename = doc.CreateElement("Sitename"); sitename.InnerText = SiteName; main.AppendChild(sitename); //Create IMO element XmlElement imo = doc.CreateElement("IMO"); imo.InnerText = IMO; main.AppendChild(imo); DataTable dt = new DataTable(); for (int i = 0; i < dataGridView1.Columns.Count; i++) { dt.Columns.Add("column" + i.ToString()); } foreach (DataGridViewRow row in dataGridView1.Rows) { DataRow dr = dt.NewRow(); for (int j = 0; j < dataGridView1.Columns.Count; j++) { dr["column" + j.ToString()] = row.Cells[j].Value ; } dt.Rows.Add(dr); } //Create DataSet and add the datatable DataSet ds = new DataSet(); ds.Tables.Add(dt); //Give the file name for where to write to. ds.WriteXml(@"C:\Users\NLRAGIL\Documents\10 - VibroManager\" + filename); //Show example for debugging doc.Save(@"C:\Users\NLRAGIL\Documents\10 - VibroManager\" + filename); System.Console.WriteLine(doc.InnerXml); }

EXTRA CLARIFICATION: The form I have looks as below:额外澄清:我的表格如下所示: 客户资料

The Textbox in the groupbox "Client Information" I'm able to save in a XML file.我可以将groupbox “客户信息”中的Textbox保存在 XML 文件中。 By altering the value of the numeric control I can express how much machine the particular client has.通过改变数值控制的值,我可以表达特定客户拥有多少机器。 And the DataGridView gets more or less rows.并且DataGridView获得或多或少的行。 But the information from the DataGridView I'm unable to append to the created XML file.但是来自DataGridView的信息我无法附加到创建的 XML 文件中。

So the information from "Machine Name", "Serial No" etc I can't add to the XML file.因此,我无法将“机器名称”、“序列号”等信息添加到 XML 文件中。

This is what I wanted to do, so later on in the program I can add certain measurements of each machine to it and store also in the same file.这就是我想做的,所以稍后在程序中我可以将每台机器的某些测量值添加到它并存储在同一个文件中。

But whatever I do my XML file looks like this:但无论我做什么,我的 XML 文件看起来都是这样的: 在此处输入图像描述

I hope I explained it better now sorry for the confusion我希望我现在解释得更好了,很抱歉造成混乱

Your question is Add the contents of a DataGridView to an existing XML file and you say your first issue is that your ForNext loop is not giving you the column names and your second issue is that the code fails to serialize the record to an XML file on disk.您的问题是将 DataGridView 的内容添加到现有 XML 文件中,您说第一个问题是ForNext循环没有为您提供列名,第二个问题是代码无法将记录序列化为 XML 文件磁盘。 These two goals can be simplified by using Data Binding .这两个目标可以通过使用数据绑定来简化。 This decouples your data from the view, making it easier to process.这将您的数据与视图分离,使其更易于处理。 I would like to give you some insight if you wanted to try it out using the CompanyProfile in your code.如果您想在代码中使用CompanyProfile进行尝试,我想给您一些见解。

First, a CompanyProfile class declares the intended public properties:首先, CompanyProfile类声明了预期的public属性:

public class CompanyProfile
{
    public string CompanyName { get; set; } 
    public string SiteName { get; set; }
    public string IMO { get; set; } = "Some Value";
} 

Next, in your MainForm class a BindingList<CompanyProfile> is declared and attached to the DataGridView like this:接下来,在MainForm类中声明一个BindingList<CompanyProfile>并将其附加到DataGridView ,如下所示:

BindingList<CompanyProfile> DataSource = new BindingList<CompanyProfile>();
protected override void OnHandleCreated(EventArgs e)
{
    base.OnHandleCreated(e);
    if(!DesignMode)
    {
        // Attach the data source to the view. Now changes to source records refresh in the view.
        dataGridView1.DataSource = this.DataSource;
        // Adding one or more records will generate the columns.
        DataSource.Add(new CompanyProfile { CompanyName = "Linear Technology", SiteName = "Colorado Design Center"});
        DataSource.Add(new CompanyProfile { CompanyName = "Analog Devices", SiteName = "1-1-2"});

        // Use string indexer to get a column
        dataGridView1.Columns[nameof(CompanyProfile.CompanyName)].AutoSizeMode = dataGridViewAutoSizeColumnMode.Fill;
        dataGridView1.Columns[nameof(CompanyProfile.SiteName)].AutoSizeMode = DataGridViewAutoSizeColumnMode.Fill;

        DataGridView1.AllowUserToAddRows = false;
    }
}

The resulting DataGridView now looks like this:生成的DataGridView现在如下所示:

具有两条记录的数据网格视图

This method makes a single file from a CompanyProfile record using XmlSerializer (but this is just one approach - and you could also serialize the entire list at one time if you choose).此方法使用XmlSerializerCompanyProfile记录生成单个文件(但这只是一种方法 - 如果您选择,您也可以一次序列化整个列表)。

private void CreateClientFile(CompanyProfile companyProfile, string fileName)
{
    System.Xml.Serialization.XmlSerializer x = new System.Xml.Serialization.XmlSerializer(typeof(CompanyProfile));
    using (var writer = new StreamWriter(fileName))
    {
        x.Serialize(writer, companyProfile);
    }
    // Open the file to view the result
    Process.Start("notepad.exe", fileName);
}

Now, iterate a ForNext loop on the DataSource not the DataGridView .现在,在DataSource而不是DataGridView上迭代ForNext循环。 You no longer need to worry about columns because you have the bound properties instead.您不再需要担心列,因为您有绑定的属性。

private void btnSerialize_Click(object sender, EventArgs e)
{
    var appData = Path.Combine(
            Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData),
            "datagridview_to_xml");
    Directory.CreateDirectory(appData);

    // Iterate the datasource list, not the DataGridView.
    foreach (CompanyProfile companyProfile in DataSource)
    {
        CreateClientFile(
            companyProfile,
            fileName: Path.Combine(appData,
            $"{companyProfile.CompanyName}_{companyProfile.SiteName}.xml")
        );
    }
}

Clicking the [Serialize] button reveals the two files.单击 [Serialize] 按钮会显示这两个文件。

在此处输入图像描述

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM