我正在制作和App从excel工作簿中读取数据如下:
excel包含有关工程量清单(BOQ)的数据,其中我有大约4或5列包含数据但在BOQ表中有分区,其中有Civil,Architecture,Mechanical,Electrical,...等。每个部门都在单独的工作表中。
我的应用程序有一个DataGridView和一个Combobox,一旦从组合框中选择一个分区,组合框将由工作表(分区)的名称填充,DataGridView将由该分区中的数据重新生成。
我已经编写了一个代码,将数据放在DataGridView
中的特定工作表中private void button1_Click(object sender, EventArgs e)
{
String name = "FF";
String constr = "Provider=Microsoft.ACE.OLEDB.12.0;" +
"Data Source=C:\\Book1.xlsx;" +
"Extended Properties='Excel 12.0 XML;" +
"HDR=YES;';";
OleDbConnection con = new OleDbConnection(constr);
OleDbCommand oConn = new OleDbCommand("Select * From [" + name + "$]", con);
con.Open();
OleDbDataAdapter sda = new OleDbDataAdapter(oConn);
DataTable data = new DataTable();
sda.Fill(data);
dataGridView1.DataSource = data;
dataGridView1.Columns[1].DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight;
foreach (DataGridViewColumn dgvc in dataGridView1.Columns)
{
dgvc.SortMode = DataGridViewColumnSortMode.NotSortable;
}
}
但我无法用工作表名称填充组合框项目。
修改
按照建议使用此代码:
DataTable schemaTable = connection.GetOleDbSchemaTable(
OleDbSchemaGuid.Tables,
new object[] { null, null, null, "TABLE" });
返回不明确的值,如下图所示:
[
在excel中,它们看起来像这样:
[
我的结果是使用此代码:
private void Form1_Load(object sender, EventArgs e)
{
foreach (string s in GetExcelSheetNames("C:\\Book1.xlsx"))
{
cboSheetName.Items.Add(s);
}
}
/// <summary>
/// This method retrieves the excel sheet names from
/// an excel workbook.
/// </summary>
/// <param name="excelFile">The excel file.</param>
/// <returns>String[]</returns>
private String[] GetExcelSheetNames(string excelFile)
{
OleDbConnection objConn = null;
System.Data.DataTable dt = null;
try
{
// Connection String. Change the excel file to the file you will search.
String connString = "Provider=Microsoft.ACE.OLEDB.12.0;" +
"Data Source=" + excelFile + ";" +
"Extended Properties='Excel 12.0 XML;" +
"HDR=YES;';";
// Create connection object by using the preceding connection string.
objConn = new OleDbConnection(connString);
// Open connection with the database.
objConn.Open();
// Get the data table containg the schema guid.
//dt = objConn.GetOleDbSchemaTable(OleDbSchemaGuid.Tables, null);
dt = objConn.GetOleDbSchemaTable(OleDbSchemaGuid.Tables, null);
if (dt == null)
{
return null;
}
String[] excelSheets = new String[dt.Rows.Count];
int i = 0;
// Add the sheet name to the string array.
foreach (DataRow row in dt.Rows)
{
excelSheets[i] = row["TABLE_NAME"].ToString();
i++;
}
// Loop through all of the sheets if you want too...
for (int j = 0; j < excelSheets.Length; j++)
{
// Query each excel sheet.
}
return excelSheets;
}
catch (Exception ex)
{
return null;
}
finally
{
// Clean up.
if (objConn != null)
{
objConn.Close();
objConn.Dispose();
}
if (dt != null)
{
dt.Dispose();
}
}
}
答案 0 :(得分:1)
为什么不使用Com对象?
以下是我在excel中获取工作表名称的方法:
List<string> workSheets = new List<string>();
if(xlsApp==null)
xlsApp = new Microsoft.Office.Interop.Excel.ApplicationClass();
Workbook book = xlsApp.Workbooks.Open(file.FullName, 0, true, 5, "", "", true, XlPlatform.xlWindows, "\t", false, false, 0, true, 1, 0);
foreach (Worksheet sheet in book.Worksheets)
{
workSheets.Add(sheet.Name);
}
xlsApp.Workbooks.Close();
xlsApp.Quit();
答案 1 :(得分:0)
显然,您只需要过滤$
个已结束的名称,它们将始终按字母顺序排列:
var sheetNames = cn.GetSchema("TABLES").AsEnumerable().Select(r => r.Field<string>("TABLE_NAME")).Where(n => n.EndsWith("$'")).Select(n => n.Substring(1, n.Length-3)).ToList();