C# |如何在 DataGrindView 上显示 Excel 个工作表?

C# | How to display Excel sheets on DataGrindView?

我正在尝试在 DataGrindView 上显示 Excel sheet。我在 Internet 上找到了解决方案,但在尝试浏览 Excel 文件时出现错误。有人能帮我解决这个问题吗?

浏览按钮代码如下:

private void btnBrowse_Click(object sender, EventArgs e)
        {
            using (OpenFileDialog openFileDialog = new OpenFileDialog() { Filter = "Excel 97-2003 Workbook|*.xls|Excel Workbook|*.xlsx" })
            {
                if (openFileDialog.ShowDialog() == DialogResult.OK)
                {
                    txtFilename.Text = openFileDialog.FileName;
                    using (var stream = File.Open(openFileDialog.FileName, FileMode.Open, FileAccess.Read))
                    {
                        using (IExcelDataReader reader = ExcelReaderFactory.CreateReader(stream))
                        {
                            DataSet result = reader.AsDataSet(new ExcelDataSetConfiguration()
                            {
                                ConfigureDataTable = (_) => new ExcelDataTableConfiguration() { UseHeaderRow = true }
                            });
                            tableCollection = result.Tables;
                            cboxSheet.Items.Clear();
                            foreach (DataTable table in tableCollection)
                                cboxSheet.Items.Add(table.TableName);//add sheet to combobox
                        }
                    }
                }
            }
        }

编辑:

你好,

这是我第一次在 Whosebug 上发帖,对于我的错误深表歉意。

我将对项目和错误进行更详细的解释。

This's my Form Application format

这是表单代码。

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.IO;
using ExcelDataReader;
using System.Data.OleDb;

namespace emailsender
{
    public partial class Form2 : Form
    {

        public Form2()
        {
            InitializeComponent();
        }

        private void Form2_Load(object sender, EventArgs e)
        {

        }



        private void cboxSheet_SelectedIndexChanged(object sender, EventArgs e)
        {

            dataGridView1.DataMember = cboxSheet.SelectedItem.ToString();
        }

        private void btnBrowse_Click(object sender, EventArgs e)
        {
            using (OpenFileDialog openFileDialog = new OpenFileDialog() { Filter = "Excel 97-2003 Workbook|*.xls|Excel Workbook|*.xlsx" })
            {
                if (openFileDialog.ShowDialog() == DialogResult.OK)
                {
                    txtFilename.Text = openFileDialog.FileName;
                    using (var stream = File.Open(openFileDialog.FileName, FileMode.Open, FileAccess.Read))
                    {
                        using (IExcelDataReader reader = ExcelReaderFactory.CreateReader(stream))
                        {
                            DataSet result = reader.AsDataSet(new ExcelDataSetConfiguration()
                            {
                                ConfigureDataTable = (_) => new ExcelDataTableConfiguration() { UseHeaderRow = true }
                            });
                            //tableCollection = result.Tables;
                            cboxSheet.Items.Clear();
                            foreach (DataTable table in result.Tables)
                                cboxSheet.Items.Add(table.TableName);//add sheet to combobox
                            dataGridView1.DataSource = result;
                            cboxSheet.SelectedIndex = 0;
                        }
                    } 
                }
            }
        }
    }
}

我尝试了 @JohnG's 示例,但是当我 select 使用文件资源管理器打开文件并按下打开按钮时,我得到了同样的错误。

System.NotSupportedException: 'No data is available for encoding 1252. For information on defining a custom encoding, see the documentation for the Encoding.RegisterProvider method.

我不太明白我错过的重点...

你的问题有点不清楚......标题说你想“在DataGridView上显示Excel表” ......这当然是可行的,但是,我在试图将 DataGridView 设置为 Excel 工作表之一的代码中看不到任何地方。发布的代码确实成功地将 selected Excel 文件读入 DataSet. 然后代码将每个工作表名称作为一个项目添加到组合框中 cboxSheet.

这一切似乎都有效。因此,鉴于您的问题,我假设在包含已发布代码填充的 ComboBox 的同一 Form 上有一个 DataGridView。我假设您希望用户能够从组合框中 select 一个特定的工作表,然后将该工作表显示在 DataGridView. 如果这是您想要的,那么幸运的是,您拥有大部分辛苦了……即创建一个 DataSet,其中 DataSet 中的每个 DataTable 都是来自 selected Excel 文件的工作表之一。

假设在Form上有一个DataGridView,代码需要在读取Excel文件后将其设置为DataSource。幸运的是,代码正在创建一个名为 resultDataSet,我们可以将其用作网格的 DataSource。像……

dataGridView1.DataSource = result;

这会将网格的 DataSource 设置为 DataSet. 为了显示 DataSet 中的特定 DataTable,代码需要设置网格 DataMember 属性 到我们要显示的 DataTable 的名称...幸运的是,我们将所有这些名称方便地存储在组合框中。

因此,在代码设置网格的DataSource后,我们也可以将组合框selection设置到数据集中的第一个table,然后设置网格的DisplayMamber 在网格中显示 selected 工作表……或者……因为我们知道我们希望网格在用户更改组合中的 selection 时显示不同的 table框,无论如何我们都必须将 up/subscribe" 连接到 ComboBoxes SelectedIndexChanged 事件。

因此,在设置网格数据源后,如果我们简单地将组合框 selected 项设置为组合框中的第一项,SelectedIndexChanged 事件应该负责休息。组合框 SelectedIndexChanged 事件只需要一行代码即可更改显示的网格 table。它可能看起来像……

private void cboxSheet_SelectedIndexChanged(object sender, EventArgs e) {
  dataGridView1.DataMember = cboxSheet.SelectedItem.ToString();
}

连接组合框SelectedIndexChanged事件后,您当前的代码只需添加如下所示的两行。请注意,我删除了 tableCollection,因为它不需要。

private void ReadExcelFileFillCombo() {
  using (OpenFileDialog openFileDialog = new OpenFileDialog() { Filter = "Excel 97-2003 Workbook|*.xls|Excel Workbook|*.xlsx" }) {
    if (openFileDialog.ShowDialog() == DialogResult.OK) {
      txtFilename.Text = openFileDialog.FileName;
      using (var stream = File.Open(openFileDialog.FileName, FileMode.Open, FileAccess.Read)) {
        using (IExcelDataReader reader = ExcelReaderFactory.CreateReader(stream)) {
          DataSet result = reader.AsDataSet(new ExcelDataSetConfiguration() {
            ConfigureDataTable = (_) => new ExcelDataTableConfiguration() { UseHeaderRow = true }
          });
          //tableCollection = result.Tables;
          cboxSheet.Items.Clear();
          foreach (DataTable table in result.Tables)
            cboxSheet.Items.Add(table.TableName);//add sheet to combobox
          dataGridView1.DataSource = result;
          cboxSheet.SelectedIndex = 0;
        }
      }
    }
  }
}

我希望这是有道理的。

根据 OP 更新和评论进行编辑

我只能猜测您收到所显示错误的原因是因为您“创建”了错误“类型”的应用程序。我假设您当前的应用程序是使用 .Net“核心”应用程序创建的。据我了解,.Net Core 使用了不同的“编码”,这导致了您看到的错误。我建议你看一下 SO 问题....

System.NotSupportedException: No data is available for encoding 1252

如果您想使用 .Net Core 应用程序,那么您可能需要遵循上述答案中的建议。但是,如果您创建“.Net Framework”而不是“.Net”应用程序,我相信这会解决问题。下面是使代码正常工作所需的正确应用程序的图片。注意...红色不是你想要的,绿色...“.Net Framework”是你想要使用的。