2010-09-28 75 views
6

首先,我想說我在這裏深陷困境,因爲我只是對公司中其他人編寫的代碼進行了一些更改,使用OleDbDataAdapter與Excel進行「交談」,我對此並不熟悉。有一個錯誤我不能遵循。使用OleDbDataAdapter從Excel工作表中獲取數據的問題

我想用OleDbDataAdapter讀取大約450行的excel文件。

在代碼中,它的完成這樣的:

connection = new OleDbConnection("Provider=Microsoft.Jet.OLEDB.4.0;" + "Data Source='" + path + "';" + "Extended Properties=\"Excel 8.0;HDR=Yes;IMEX=1;\""); 
connection.Open(); 
OleDbDataAdapter objAdapter = new OleDbDataAdapter(objCommand.CommandText, connection); 
objAdapter.Fill(objDataSet, "Excel"); 

foreach (DataColumn dataColumn in objTable.Columns) { 
    if (dataColumn.Ordinal > objDataSet.Tables[0].Columns.Count - 1) { 
    objDataSet.Tables[0].Columns.Add(); 
    } 
    objDataSet.Tables[0].Columns[dataColumn.Ordinal].ColumnName = dataColumn.ColumnName; 
    objImport.Columns.Add(dataColumn.ColumnName); 
} 

foreach (DataRow dataRow in objDataSet.Tables[0].Rows) { 
    ... 
} 

一切似乎是工作,除了一件事罰款。第二列填充大多數四位數字,如6739,3920等等,但是fice行具有像8201NO和8205NO這樣的字母數字值。這五個單元被報告爲具有空白內容而不是其字母數字內容。我已經檢查了excel,並且此列中的所有單元格都標記爲文本。

這是一個xls文件,而不是xlsx。

有沒有人有任何線索爲什麼這些單元格在DataRow中顯示爲空白,但數字的單元格顯示正常?還有其他列顯示字母數字內容,顯示得很好。

+0

感謝所有幫助我這個問題。你讓我明白爲什麼會發生這種情況,所以我可以找到適當的解決方案。我仍然認爲它的工作方式是相當可怕的,但那是另一回事:) – 2010-09-29 07:52:53

回答

8

發生什麼事情是,excel試圖根據該列中的前幾個值將數據類型分配給電子表格列。我懷疑,如果你看看該列中的屬性,它會說它是一個數字列。

當您開始嘗試使用jet查詢電子表格時,問題就出現了。當它認爲它正在處理一個數字列,並且它發現一個varchar值時,它將悄然返回任何內容。甚至沒有隱瞞錯誤信息。

作爲一種可能的解決方法,您可以將其中一個字母數字值移至第一行數據,然後嘗試解析。我懷疑你會開始獲得字母數字行的值然後...

看看this article。它在這個問題上更詳細。它也談到了可能的解決辦法是:

然而,按照JET文件,我們 可以覆蓋註冊表設置直通 連接字符串,如果我們設置 IMEX = 1(作爲擴展 一部分屬性),所述射流將設置的所有 列類型爲UNICODE VARCHAR或 ADVARWCHAR不論 「ImportMixedTypes」鍵value.hey

+0

我已經測試過了,現在確實如果我把第一行字母數字化,那麼它的工作方式與預期的一樣。我的問題是,我不能將此作爲一般規則,因爲客戶會在自己的工作表中閱讀。但是,我的解決方案是「作弊」,以便在連接字符串中更改HDR = No以確保讀取字母數字標題以創建字母數字列,然後剪切生成的DataTable的第一行。這很不好,但我在這裏沒有看到其他的選擇。非常感謝您的幫助,讓我朝着正確的方向前進。 – 2010-09-29 07:49:10

+0

非常偷偷摸摸。如果它工作,它的工作! – 2010-09-29 14:40:35

1

IMEX=1意味着「讀混合數據爲文本」。

但是有一些問題。 Jet只會使用多行來確定數據是否混合,如果是這樣,這些行都是數字,你會得到這種行爲。

詳見connectionstrings.com

退房的[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Jet\4.0\Engines\Excel]位於註冊表REG_DWORD 「TypeGuessRows」。這是不讓Excel使用前8行來猜測列數據類型的關鍵。將此值設置爲0以掃描所有行。這可能會損害性能。另請注意,添加IMEX = 1選項可能會導致IMEX功能在8行之後設置。使用IMEX = 0來確保強制註冊表TypeGuessRows = 0(掃描所有行)。

+0

我不知道Jet是如何在Excel中公開的,但在Access中,您可以在運行時在Jet數據庫引擎的當前實例中更改這些內容,而無需更改註冊表並重新啓動Access。 – 2010-09-29 00:35:27

+0

感謝您提供此信息。它工作但出人意料地很慢,所以我不得不採用「讀取和處理標題」的方法。 – 2010-09-29 07:51:48

1

我會建議不要使用OleDb數據提供程序的東西訪問Excel,如果你可以幫助它。除了問題之外,我只有其他人指出的原因。當您處理大型電子表格時,性能往往會非常糟糕。

你可以試試這個開源的解決方案: http://exceldatareader.codeplex.com/

+0

我完全同意你的看法。我認爲這是非常可怕的,但在這種情況下,我沒有任何選擇,因爲我被分配到修復現有程序中的這個錯誤,並沒有分配時間來做任何大的重構。如果我以後需要從頭開始,我會記住你的鏈接。 – 2010-09-29 07:50:34

相關問題