所以我有一個應用程式,它將創建一個具有指定名稱的 excel 檔案,我希望我的應用程式在啟動時在我的應用程式 DataGridView 中讀取并顯示這個檔案,我到目前為止的代碼如下:
private void OpenExcelFile()
{
System.Data.DataTable dt = new System.Data.DataTable(); //container for our excel data
foreach (var file in Directory.GetFiles(this.ExcelFolderPath).Where(p => p.Contains("Contacts")))
{
try
{
//Create Object for Microsoft.Office.Interop.Excel that will be use to read excel file
Microsoft.Office.Interop.Excel.Application excelApp = new Microsoft.Office.Interop.Excel.Application();
Microsoft.Office.Interop.Excel.Workbook excelWorkbook = excelApp.Workbooks.Open(file);
Microsoft.Office.Interop.Excel._Worksheet excelWorksheet = excelWorkbook.Sheets[1];
Microsoft.Office.Interop.Excel.Range excelRange = excelWorksheet.UsedRange;
int rowCount = excelRange.Rows.Count; //get row count of excel data
int colCount = excelRange.Columns.Count; // get column count of excel data
GC.Collect();
GC.WaitForPendingFinalizers();
Marshal.ReleaseComObject(excelRange);
Marshal.ReleaseComObject(excelWorksheet);
//quit apps
excelWorkbook.Close();
Marshal.ReleaseComObject(excelWorkbook);
excelApp.Quit();
Marshal.ReleaseComObject(excelApp);
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
這將搜索并找到我的檔案,還將計算表中的列數和行數,底部的代碼將關閉 excel 行程,此后我不確定下一步是什么,我知道我必須打開excel檔案,但不確定如何執行此操作。任何幫助表示贊賞。
uj5u.com熱心網友回復:
如果您在使用 Interop 時遇到困難,那么下面的代碼可能會有所幫助。當前代碼中的一個問題是代碼關閉和釋放 Excel COM 物件的方式。當然,您確實在一個try/catch塊中擁有此代碼,但是,如果代碼在到達關閉和釋放代碼之前崩潰……那么這些 COM 物件不會被關閉或釋放,最終成為泄漏資源。
我建議您將關閉和發布代碼放在陳述句的finally部分中。try/catch/finally這樣,即使代碼在使用 Excel 檔案時崩潰,COM 物件在技術上“應該”被釋放。
看來您已經在代碼的開頭定義了一個DataTable呼叫......但它從未使用過。dt所以,讓我們使用它……我已將其重命名為NewDT.
第一步是創建DataTable列。我們將假設 Excel 檔案中的第一行是標題行。我們將使用第一行作為列名。我們還將假設所有列“型別”都是一個string型別。strings如果此代碼中需要,您可以輕松地將 轉換為正確的型別。但是,您需要事先知道這些“型別”是什么以及它們屬于“哪些”列。在這個例子中,它們都是strings為了簡化代碼。
在我們創建列DataTable之后,剩下的就是回圈遍歷 Excel 單元格并獲取單元格string值并將其添加到表格中。這聽起來直截了當而且很簡單,但是,您要記住一個警告……回圈遍歷 Excel 范圍可能很昂貴……如果可能的話,我會避免使用它。
為了避免這種情況,我們可以使用一個二維object陣列并抓取整個UsedRange并將其讀入這個陣列......就像......
excelRange = excelWorksheet.UsedRange;
object[,] data = (object[,])excelRange.Cells.Value;
這是我們將遍歷以獲取單元格值的陣列。如果 Excel 檔案很大,這將加快速度。特別注意:由于我們將回圈遍歷此物件陣列data,您應該知道它的起始索引為一 (1) 而不是零 (0)。這來自 Excel,我們只需要注意這一點。
陣列的第一行包含列名。因此,我們想使用這一行來定義NewDT DataTable. 這個簡單的回圈看起來像……
for (int i = 1; i <= colCount; i ) {
if (data[1, i] != null) {
NewDT.Columns.Add(data[1, i].ToString(), typeof(string));
}
else {
NewDT.Columns.Add("", typeof(string));
}
}
注意:在此處檢查“重復”列名稱以避免重復名稱例外可能是明智之舉。我會把這個留給你去做。
接下來,我們要遍歷陣列中的每一行并收集列/單元格值并將該行添加到NewDT DataTable. 這可能看起來像……
DataRow curRow = null;
for (int i = 2; i <= rowCount; i ) {
curRow = NewDT.NewRow();
for (int j = 1; j <= colCount; j ) {
if (data[i, j] != null) {
curRow[j - 1] = data[i, j].ToString();
}
}
NewDT.Rows.Add(curRow);
}
注意curRow的列/單元格索引是“J – 1”,因為DataTable列索引從零 (0) 開始。
那應該差不多了。現在您可以將DataTableas a添加DataSource到網格中dataGridView1.DataSource = NewDT;……
完整的更新代碼如下……
string ExcelFolderPath = @"PathToYourFile";
private void Form1_Load(object sender, EventArgs e) {
OpenExcelFile();
}
private void OpenExcelFile() {
DataTable NewDT;
foreach (var file in Directory.GetFiles(this.ExcelFolderPath).Where(p => p.Contains("Contacts"))) {
Microsoft.Office.Interop.Excel.Application excelApp = null;
Microsoft.Office.Interop.Excel.Workbook excelWorkbook = null;
Microsoft.Office.Interop.Excel._Worksheet excelWorksheet = null;
Microsoft.Office.Interop.Excel.Range excelRange = null;
try {
excelApp = new Microsoft.Office.Interop.Excel.Application();
excelWorkbook = excelApp.Workbooks.Open(file);
excelWorksheet = excelWorkbook.Sheets[1];
excelRange = excelWorksheet.UsedRange;
int rowCount = excelRange.Rows.Count;
int colCount = excelRange.Columns.Count;
object[,] data = (object[,])excelRange.Cells.Value;
NewDT = new DataTable();
for (int i = 1; i <= colCount; i ) {
if (data[1, i] != null) {
NewDT.Columns.Add(data[1, i].ToString(), typeof(string));
}
else {
NewDT.Columns.Add("", typeof(string));
}
}
DataRow curRow = null;
for (int i = 2; i <= rowCount; i ) {
curRow = NewDT.NewRow();
for (int j = 1; j <= colCount; j ) {
if (data[i, j] != null) {
curRow[j - 1] = data[i, j].ToString();
}
}
NewDT.Rows.Add(curRow);
}
dataGridView1.DataSource = NewDT;
}
catch (Exception ex) {
MessageBox.Show(ex.Message);
}
finally {
//GC.Collect();
//GC.WaitForPendingFinalizers();
if (excelRange != null) {
Marshal.ReleaseComObject(excelRange);
}
if (excelWorksheet != null) {
Marshal.ReleaseComObject(excelWorksheet);
}
if (excelWorkbook != null) {
excelWorkbook.Close();
Marshal.ReleaseComObject(excelWorkbook);
}
if (excelApp != null) {
excelApp.Quit();
Marshal.ReleaseComObject(excelApp);
}
}
}
}
我希望這是有道理的并有所幫助。
轉載請註明出處,本文鏈接:https://www.uj5u.com/net/496693.html
