将 DataGridView 记录导出到 Excel

Posted

技术标签:

【中文标题】将 DataGridView 记录导出到 Excel【英文标题】:Exporting DataGridView records to Excel 【发布时间】:2021-11-10 13:16:36 【问题描述】:

我有一个包含多个列和不同报告类型的 datagridview,其中我有一种将记录导出到 Excel 电子表格的方法,在这个 datagridview 中,我根据所选的报告类型留下了一些列,例如:visible = false

在电子表格的导出方法中,我有一个仅考虑可见单元格的验证,是的,但它不起作用。

        int XLRow = 1;
        int XLCol = 1;

        // Export header
        for (int i = 0; i < datagrid.Columns.Count; i++)
        
            if (datagrid.Columns[i].Visible == true)
                xlWorkSheet.Cells[XLRow, XLCol++] = datagrid.Columns[i].HeaderText;
        

        XLRow = 2;
        XLCol = 1;

        // Controls for scrolling through records do DataGridView
        for (int i = 0; i < datagrid.RowCount; i++)
        
            for (int j = 0; j < datagrid.ColumnCount; j++)
            
                DataGridViewCell cell = datagrid[j, i];
                string conteudo = string.Empty;
                if ((cell.Value != null) && (!string.IsNullOrEmpty(cell.Value.ToString())) && cell.Visible == true)
                
                    conteudo = cell.Value.ToString();
                    if ((Funcoes.EhNumerico(conteudo)) && (conteudo.Length > 8))
                    
                        conteudo = string.Concat("'", conteudo);
                    
                    xlWorkSheet.Cells[XLRow, XLCol++] = conteudo;
                
                XLRow++;
                XLCol = 1;
            
        

电子表格以白色的visible = false 列离开,如下所示:

我该如何解决这个问题?

【问题讨论】:

电子表格没有接收到不可见的 gridview 列;您将可见的 gridview 列放在错误的电子表格列中。 在第一个 for 循环遍历列中,代码检查该列是否可见,如果可见,则添加标题。这样做的问题是,由于您使用i 作为工作表的索引,因此可能会跳过不可见的列,但是,索引i 仍然递增……意味着下一列将使用i + 1这就是您在 Excel 文件中看到空白列的原因。同样的想法也适用于添加网格单元的代码。我建议您为 Excel 索引“仅”创建几个 int 变量,并严格使用 ij 作为网格单元格的索引……。 但是我不会将i和j的值存储在这些建议的变量中吗?你能帮我想象一下编码吗? 【参考方案1】:

换句话说......在第一个for循环中......如果列不可见......那么你不想增加i......这显然会弄乱for循环。因此,我建议创建两 (2) 个int 变量...int XLRowint XLColumn,然后将这些索引专门用于工作表。然后像您的代码一样使用ij 遍历网格列,但是,当发现不可见的列时,您不想增加XLCol 索引。

loopsij 变量同时用作工作表列的索引将是一项具有挑战性的工作,因为它们可能是完全“不同”的索引。这就是为什么我说将它们与 git go “分开”并保持简单。像……

根据 OP 评论编辑……

我有代码可以“增加”XLCol“内部”if 语句,该语句检查null 单元格值或空字符串单元格值……这意味着单元格是null 还是空的……然后XLCol 不会增加。 xlWorkSheet.Cells[XLRow, XLCol++] = conteudo; 行应该在 if 语句的“外部”。我已经编辑了代码,现在它应该可以在“空”单元格中正常工作了。

int XLRow = 1;
int XLCol = 1;
for (int i = 0; i < datagrid.Columns.Count; i++) 
  if (datagrid.Columns[i].Visible == true)
    xlWorkSheet.Cells[XLRow, XLCol++] = datagrid.Columns[i].HeaderText;

XLRow = 2;
XLCol = 1;
for (int i = 0; i < datagrid.RowCount; i++) 
  for (int j = 0; j < datagrid.ColumnCount; j++) 
    if (datagrid.Columns[j].Visible) 
      DataGridViewCell cell = datagrid[j, i];
      string conteudo = string.Empty;
      if ((cell.Value != null) && (!string.IsNullOrEmpty(cell.Value.ToString()))) 
        conteudo = cell.Value.ToString();
        if ((Funcoes.EhNumerico(conteudo)) && (conteudo.Length > 8)) 
          conteudo = string.Concat("'", conteudo);
        
        //xlWorkSheet.Cells[XLRow, XLCol++] = conteudo; <- XLCol incremented ONLY if cell is not null or empty and this is wrong
      
      xlWorkSheet.Cells[XLRow, XLCol++] = conteudo;
    
  
  XLRow++;
  XLCol = 1;

【讨论】:

标题符合您的建议,但是我无法整理记录,一张一张地乱七八糟,我添加了一张照片供您查看。 对不起,我没有测试这个...请给我一点时间来测试它。同时,您可以在您的更改中添加代码吗? 没问题,感谢您的帮助。我更新了代码。 @Favieri ... 很高兴你让它工作了......我在列循环内增加了最后两行代码,它应该在列循环之外......。对于那个很抱歉。另外提醒一下……最好使用“编辑”标题将更新的代码“添加”到问题中,并解释额外的更新代码,而不是“删除”现有代码。删除之前的代码可能会使其他可能阅读 cmets 的人感到困惑。例如,如果您现在阅读我的第二条评论……查看当前代码时没有任何意义。只是提醒一下。 @Favieri ...感谢您指出我的错误,我已经更新了答案中的代码以正确增加XLCol

以上是关于将 DataGridView 记录导出到 Excel的主要内容,如果未能解决你的问题,请参考以下文章

将datagridview导出到csv文件

将 DataGridView 导出到文本文件,保持列对齐

使用互操作将 datagridview 导出到 excel

将 dataGridView 数据导出到 excel 时出现错误

Python 2.7_初试连接Mysql查询数据导出到exce_20161216

如何使用 Excel 对象将 DataGridView 数据导出到 Excel