ADO.NET(OleDb)读取Excel表格时的一个BUG

如果我们有例如以下一个Excel表格:

如今要使用C#程序读取其内容:

using System;

using System.Data.OleDb;

namespace Skyiv.Ben.Test

{

  sealed class ExcelTest

  {

    static void Main()

    {

      try

      {

        using (OleDbConnection conn = new OleDbConnection("Provider=Microsoft.Jet.OLEDB.4.0;Extended Properties=\"Excel 8.0;HDR=yes\";Data Source=Std"))

        {

          conn.Open();

          OleDbCommand comm = new OleDbCommand("SELECT [ID],[NAME] FROM [Sheet1$]", conn);

          using (OleDbDataReader r = comm.ExecuteReader())

          {

            while (r.Read())

            {

               int id = Convert.ToInt32(r.GetValue(0));

               string name = Convert.ToString(r.GetValue(1));

               Console.WriteLine("{0}:\t{1}", id, name);

            }

          }

        }

      }

      catch (Exception ex)

      {

        Console.WriteLine("错误: " + ex.Message);

      }

    }

  }

}

该程序的执行结果例如以下:

看来在读取单元格“B3”时返回了“DBNull”,而不是正确的“1768”。

使用我的博客园发表的一篇随笔“数据库小工具(C#)”中给出的 OleDb.exe 查看了一下:

确实,该 Execl 表格中有 2 个“DBNull”值,再用该工具查看一下其结构:

发现其第一列“ID”的数据类型是“double”,第二列“NAME”的数据类型是“string”。

经分析。“DBNull”都出如今其数据类型与列的数据类型不相符的单元格中。

看来。问题的症结就在这里了。我们知道,Excel 表格并是不真正的数据库,不像真正的数据库一样每一个字段(列)都有一个特定的数据类型。而是由ADO.NET通过扫描该表格的开头几行来猜測其每一列的数据类型,这样。当某列中有些单元格的数据类型与该列数据类型不一致时。就出问题了。该单元格的值就变成的“DBNull”。

这个问题来源于我的实际工作。在工作中,须要分析一张业务部门提供的 Excel 表格中的数据,该表格有好几千个数据行。当中有些列绝大部分的值是数字型。但当中有一些数字存储为文本格式。而有些列绝大部分的值是字符型,但有少数单元格的值是数字。这样,我的分析程序就不能工作了。我眼下的解决方式是将该 Excel 表格另存为文本文件(制表符分隔),然后在 C# 程序中读取该文本文件。

另一种方法就是在 Excel 表格中选中整列。然后“将存为文本的数字转换为数字”。例如以下所看到的:

可是,我并没有找到一个简便的方法来“将数字转换为文本”。

不知在 ADO.NET 中有没有办法在不改变原始 Excel 表格的情况下。正确读取其列中有单元格的数据类型不一致的 Excel 表格中的数据?假设谁知道的话,恳请告诉我。谢谢。

不知道要通过什么途径向 Microsoft 报告这个 BUG ?

我觉得这个 BUG 的解决方式有两个:

1.  假设某一列被猜測为数字型的话,假设在该列中出现字符型的数据,假设该数据是存储为文本的数字,就直接转换为数字返回给调用者好了。

假设该数据不能转换为数字,能够返回“DBNull”,或者抛出异常。

假设某一列被猜測为字符型的话,仅仅要该列中的单元格不为空。就转换为字符型返回给调用者。

2. 在 ADO.NET 的 OleDb 连接串中提供一个属性强制指定 Excel 表格中的全部列的数据类型都为“string”,仅仅要单元格的内容不为空,就不返回“DBNull”,而返回“string”。然后由调用者自己使用 Convert.ToXXX() 方法转换到合适的数字类型。

不知大家以为然否?

时间: 2024-10-26 01:34:27

ADO.NET(OleDb)读取Excel表格时的一个BUG的相关文章

Python:读取Excel表格时出现的u'\u51c6’ 无法正确显示汉字

读取Excel后,想显示其中一行的元素,结果读出来是这样[u'\u51c6\u8003\u8bc1\u53f7', u'\u8003\u751f\u59d3\u540d'],始终不显示正常的汉字 依照网上的方法直接print()即可输出,试验后发现确实可以,不过一次只能输出一个元素,多余一个元素则依旧 后查找得知解决方法:需要用到json库 1 import json 2 #……文件的读取略去 3 #json.dumps(A).decode("unicode-escape") 4 #这

Python读取excel表格时,意外的深入理解info字典问题

import xlrd import re def excel_table_byindex(): data = xlrd.open_workbook('crawlingPhonePrice_new.xlsx') #打开一个excel表格,表格有手机名,价格 table=data.sheets()[0] nrows=table.nrows ncols=table.ncols colnames=table.row_values(0) #print(colnames) info={} #存放键值对,手

C#:使用OleDb从Excel表格中读取信息到DataTable

从Excel表格中将数据读入到DataTable数据类型中,我是通过使用OLEDB来实现的 (OLEDB是Object Linking and Embedding Database的缩写) 现有一个扩展名为xlsx的工作簿文件"节气表.xlsx",在工作表Sheet1中有24个节气的信息 本文中的示例程序(代码将在后面给出)读取这个数据表后的效果如下图: 可以看出:OleDb读入一个Excel工作表(Sheet)的数据后,工作表的第一行会变成标题,第二行起,逐行变为DataTable的

Java读取excel表格

Java读取excel表格 一般都是用poi技术去读取excel表格的,但是这个技术又是什么呢 什么是Apache POI? Apache POI是一种流行的API,它允许程序员使用Java程序创建,修改和显示MS Office文件.这由Apache软件基金会开发使用Java分布式设计或修改Microsoft Office文件的开源库.它包含类和方法对用户输入数据或文件到MS Office文档进行解码. Apache POI Apache POI是Apache软件基金会提供的100%开源库.大多

python读取excel表格生成sql语句 第一版

由于单位设计数据库表·,都用sql.不知道什么原因不用 powerdesign或者ermaster工具,建表很痛苦  作为程序猿当然要想办法解决,用Python写一个程序解决 需要用到 xlrd linux下 sudo pip install xlrd 主要是适用于db2数据库 excel 表结构 其中 number是不正确的字段类型 不知道同事为啥这么设置.这里程序里有纠错,这个程序就是将sql语句拼好. __author__ = 'c3t' # coding:utf-8 import xlr

采用OleDB读取EXCEL文件 读取数字后,字符串无法读取

很多人采用OleDB读取EXCEL文件的时候会发现,当一列数据以数字开头的时候,后面的字符串无法读取,今天就给大家分享一下解决此问题的小窍门. 1.把列标题当做数据来读取(HDR=NO设置把第一行当做数据而不是表头来处理):  string strConn = "Provider=Microsoft.ACE.OLEDB.12.0;" + "Data Source=" + fileName + ";" +                     &

C#通过OleDb读写excel表格几个要点

1,OleDbConnection 的连接字符串: 0ffice 97-2003 : strConnection = string.Format("Provider=Microsoft.Jet.OLEDB.4.0;Data Source={0};Extended Properties=\"Excel 8.0;HDR={1};IMEX={2:D}\";", ExcelFilePath, HDR, IMEX); //HDR=No 表示ADO将不把你Excel文件的第一行

C#读取Excel表格数据到DataGridView中和导出DataGridView中的数据到Excel

其实想在datagridview中显示excel表格中的数据跟读取数据库中的数据没什么差别,只不过是创建数据库连接的时候连接字段稍有差别. private void btnShow_Click(object sender, EventArgs e) { OpenFileDialog fd = new OpenFileDialog();//首先根据打开文件对话框,选择excel表格 ofd.Filter = "表格|*.xls";//打开文件对话框筛选器 string strPath;/

读取Excel表格报错问题总结(用apache POI读取,表格稍微改动就报错导入不进去)

 首先是建立在用apachePOI解析Excel时一定几率是能成功解析导入的,如果一点也不能的话,也可以参考看看我总结的原因,也许也是导致你屡次导入不能的原因之一. 这个问题是前天客户反应的,不用下载的好的模版套进内容再导入的话就报错,怎么也导入不进去,客户即想用从其他直接导出的数据导入我们的产品中用想能自己复制一些其他的内容到自己建立的excel表格中导入进去.今天晚上特意抽出时间来总结一产生这个问题的几个原因. 第一个原因就是,我最后发现我们的产品中excel导入这个组件(用apache