如何从给定行开始从Excel读取数据并获取正确的类型推断

时间:2015-05-19 17:03:22

标签: .net excel datatable ado type-inference

我使用这些连接字符串从.xls和.xlsx文件导入数据

"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=c:\file.xls;Extended Properties="Excel 8.0;HDR=YES;IMEX=0;MaxScanRows=16;Empty Text Mode=NullAsEmpty;"

"Provider=Microsoft.ACE.OLEDB.12.0;Data Source=c:\file.xlsx;Extended Properties="Excel 12.0 Xml;HDR=YES;IMEX=0;MaxScanRows=16;Empty Text Mode=NullAsEmpty;"

我在数据表中加载数据。

    Using connection As New OleDbConnection(connString)
        connection.Open()
        wsName = "myWorksheet$"

        Dim SQL As [String] = String.Format("SELECT {1} FROM [{0}]", wsName, "*")

        Dim da As New OleDbDataAdapter(SQL, connection)
        Dim ds As New DataSet
        da.Fill(ds)

        dtb = ds.Tables(0)

    End Using

如果数据在excel文件的第一行开始,我会得到正确的类型字段。不幸的是,一些excel文件(包括xls和xlsx格式)在实际数据之前可能有多行标题和其他烦恼。当它们应该是数字时,这可能会破坏Jet结尾的字样,这些字段应该是数字。

似乎不可能强制喷射从X行开始读取。

我还尝试使用DataReader前进到数据的开头,然后创建DataTable

        dtb.Load(reader)

但问题是相同的,字段类型基于第一个实际行。

因此,我询问有关如何使用从Excel文件的第x行开始的数据来获取具有相应类型字段的DataTable的建议。

1 个答案:

答案 0 :(得分:1)

这是一条你已经开始的黑暗道路。我最近一直在努力,在尝试了几个选项之后,我最终选择了ExcelDataReader。这是一个很好的.NET库,可以很好地从.xls和.xlsx文件导入数据。基本导入如下:

IExcelDataReader excelReader = default(IExcelDataReader);
using (System.IO.FileStream excelStream = new System.IO.FileStream(fileName, IO.FileMode.Open, IO.FileAccess.Read, IO.FileShare.ReadWrite)) {
    if (System.IO.Path.GetExtension(fileName).ToLower() == ".xls") {
        excelReader = ExcelReaderFactory.CreateBinaryReader(excelStream);
    } else {
        excelReader = ExcelReaderFactory.CreateOpenXmlReader(excelStream);
    }
    excelReader.IsFirstRowAsColumnNames = true;
}

// Library doesn't throw proper exceptions, create our own
if (excelReader.ExceptionMessage != string.Empty) {
    throw new ExcelReaderException(excelReader.ExceptionMessage, fileName);
}

DataSet excelPages = excelReader.AsDataSet();

我正在处理遗留代码,因此我仍然需要将导入转换为DataSet。但是,如果有机会,可以使用Sheet,Page和Cell对象。到目前为止我遇到的一个问题是我没有找到 nice 解决方法,有时库会从电子表格中导入空白行(有几次,数千次)。我们目前的解决方法是在进口后修剪它们。

对于OLEDB:我相信您可以执行注册表更新,设置OLEDB使用的预读行数,以确定列应设置的数据类型。这是一个糟糕的选择,因为必须在每台客户端计算机上完成。此外,您最有可能在基于OLEDB的Excel导入中遇到其他问题。我不记得所有这些,但它足以让我们完全抛弃它。