【问题标题】:Best way to fill DataGridView with large amount of data用大量数据填充 DataGridView 的最佳方法
【发布时间】:2010-08-26 23:07:55
【问题描述】:

我有一个 Windows 窗体,它有两个 DataGridView (DGV),每个窗体将容纳 25,000 多条记录和 21 列。我已经使用 DataAdapter 成功地从数据库中加载了每个数据,然后我尝试使用 for 循环简单地填充 DGV。每种方法花费的时间大致相同。第一次将数据填充到 DGV 中需要很长时间(7 分钟以上),而随后的时间则更加合理(约 30 秒)。所以我的问题是,用平均

【问题讨论】:

  • 你知道虚拟模式吗?您不会加载所有数据。 DGV 将告诉您“我需要记录 146-203”并且您只获取这些行。 msdn.microsoft.com/en-us/library/15a31akc.aspx
  • 谢谢乔纳森!!这听起来像我需要的。但是,我有一个问题。应用程序的下一步是比较两个 DGV。以编程方式比较它们时,我仍然可以访问整个数据集吗?

标签: c# datagridview


【解决方案1】:

DataGridView中显示数据基本上有3种方式

  • 在循环中手动创建行,就像您目前正在做的那样:正如您所注意到的,如果您有大量数据,效率会非常低

  • 使用 DataGridView 的虚拟模式,正如 Jonathan 在他的评论中所建议的那样:DGV 只创建尽可能多的行,并在用户滚动时动态更改其内容。您需要处理CellValueNeeded 事件以向DGV 提供所需的数据

  • 使用数据绑定:这是迄今为止最简单的方法。您只需使用DbDataAdapter 用数据库中的数据填充DataTable,然后将此DataTable 分配给DGV 的DataSource 属性。 DGV 可以自动创建列(AutoGenerateColumns = true),也可以手动创建(必须将列的DataPropertyName 设置为要显示的字段的名称)。在数据绑定模式下,DGV 的工作方式与虚拟模式类似,只是它负责从数据源获取数据,因此您无需做任何事情。即使对于大量行,它也非常有效

【讨论】:

    【解决方案2】:

    我认为您可以使用 DataReader 方法而不是 DataAdapter。 DataReader 是一个非常高效的单向组件,因为它只从源读取数据,并且可以循环填充数据表。

    【讨论】:

      【解决方案3】:

      如果您有大量行,例如 10 000 或更多,

      为避免性能泄漏 - 在数据绑定之前执行以下操作:

      dataGridView1.RowHeadersWidthSizeMode = DataGridViewRowHeadersWidthSizeMode.EnableResizing; 
      //or even better .DisableResizing. 
      //Most time consumption enum is DataGridViewRowHeadersWidthSizeMode.AutoSizeToAllHeaders
      dataGridView1.RowHeadersVisible = false; // set it to false if not needed
      

      数据绑定后,您可以启用它。

      【讨论】:

      • 伙计,我知道回复太晚了,但在挣扎了将近一周后,我进入了这个线程 n 设置,正如你所说的那样解决了我的问题......长寿:)
      • 在 2021 年仍然相关......不自动调整列大小可以节省大量时间......谢谢
      【解决方案4】:

      尝试使用数据表。填充。 然后使用数据视图。将其分配给 DataGridView 数据源。

      //DataView dataView = new DataView(dataTable);
      //this.Grid.DataSource = dataView;
      

      对于大文件(每秒 25000 条记录和 21 列),您将获得非常短的响应时间。 我的模板程序花了 7 秒来加载 100 000 行 * 100 列 {内容愚蠢 -> 行号为字符串}

      【讨论】:

      • 我刚刚使用 10 列、6753 行进行了测试,它花了 2:03.9174603 6735。我使用的表单是简单的,只有表单上的其他控件是一个按钮,用于最初填充 datagridview .
      • 请添加更改(“DataView”)和没有更改所需的时间。这样我们就可以比较它实际产生的差异有多大。
      【解决方案5】:

      这解决了我的问题:

      array<DataGridViewRow^>
          ^theRows = nullptr;
      if (DG->Rows->Count == 0)//First Compilation
      {
          int NUMROWS = xxx;
          theRows = gcnew array<DataGridViewRow^>(NUMROWS);
          for (int nr = 0; nr < DRH->Count; nr++)
              theRows[nr] = gcnew DataGridViewRow();
      //Do not remove the two following
          DG->Rows->AddRange(theRows);
          DG->Rows->Clear();
      }
      else //Update
      {
      
          theRows = gcnew array<DataGridViewRow^>(DG->Rows->Count);
          DG->Rows->CopyTo(theRows, 0);
          DG->Rows->Clear();
      
      }
      for(int nr=0;nr<theRows->Length;nr++)
      {
          theRows [nr]->SetValues("val1", "val2");
      }
      DG->Rows->AddRange(theRows);
      

      【讨论】:

        【解决方案6】:

        我不确定这是否正是您要问的,但我喜欢创建一个数据子集以进行初始加载,然后包含搜索功能。 使用 Visual Studio 15 和 DataSources / 数据集很容易做到这一点。 在解决方案资源管理器中,打开您的 dataset.xsd 文件。它将被命名为 DataSet.xsd 转到有问题的数据表。右键单击并添加查询。我通常做的一件事就是在我的查询中添加“TOP 1000”。 所以,select * from mytable 变成 select TOP 1000 * from mytable

        最后,双击您的表单以找到您的 _load 方法,并更改“填充”以使用您的新查询。最好用一个例子来说明这一点:

        我注释掉的第一行代码是 Vis Stud 默认创建的。 第二个是我加的,只会得到前1000条记录。

                private void Form_Customers_Load(object sender, EventArgs e)
            {
                // TODO: This line of code loads data into the 'stage2DataSet.customers' table. You can move, or remove it, as needed.
                /* this.customersTableAdapter.Fill(this.stage2DataSet.customers); */
                this.customersTableAdapter.FillBy_Top_1000(this.stage2DataSet.customers);
        
        
            }
        

        【讨论】:

        • 我真的反对使用无类型数据集。 a) 该查询将起作用,但是当您稍后更新数据集时,特别是随着数据库的增长并且开始变得难以在数据集设计器中找到特定查询时,它将覆盖您的所有查询并仅重置为默认查询.所以你必须不断地重新创建那些用户定义的查询。 b) 他们还要求您在对数据进行编码之前在每个位置填充 TableAdapter,这可能非常慢。
        猜你喜欢
        • 2020-01-08
        • 2019-01-20
        • 1970-01-01
        • 2010-10-05
        • 1970-01-01
        • 2012-04-04
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多