65.9K
CodeProject 正在变化。 阅读更多。
Home

使用 OleDb 导入文本文件(制表符、CSV、自定义)

starIconstarIconstarIconstarIcon
emptyStarIcon
starIcon

4.81/5 (11投票s)

2008年7月15日

CPOL

4分钟阅读

viewsIcon

216367

downloadIcon

6858

一个简单的类,可以帮助您开始使用 OleDb Jet Engine 导入文本文件。

引言

我一直在网上寻找一个简单好用的类来处理分隔符文件导入。我目前的工作有一个导入选项需要处理这个问题。然而,当前的实现(使用 StreamReader)还不够好。它无法处理分隔符文件中遇到的所有异常。我在网上找到了一些示例,但没有一个真正适合我的需求。我真正需要的是一个简单的示例,我可以对其进行扩展以满足我的需求。所以,作为我这样的开发者,我创建了自己的类来导入分隔符文件。完成之后,我想把它作为一个示例分享给其他人。

使用 StreamReader

处理分隔符文件的最简单方法是使用 StreamReader 对象。然后,您只需打开文件,读取每一行,然后使用 split 方法获取各种列值。例如

public void ImportDelimitedFile(string filename, string delimiter)
{
    using (StreamReader file = new StreamReader(filename))
    {
        string line;

        while ((line = file.ReadLine()) != null)
        {
            if (line.Trim().Length > 0)
            {
                string[] columns = line.Split(delimiter, StringSplitOptions.None);
         
                // Add code to process the columns
            }
        }
    }
}

在很多情况下,这都能正常工作,但这种情况存在局限性

  • 分割一行到列中很困难。例如,当您使用逗号分隔文件 (CSV) 时,一个列中可能包含逗号。因此,使用简单的 string.Split 不是一个选项。
  • 当您只需要某些列或行时,您需要扫描所有行,处理所有行并过滤掉您不需要的内容。
  • 无法返回到上一行。

使用 Jet 引擎

当您使用 Jet 引擎时,上述问题将得到解决。以下代码演示了如何处理 CSV 文件

public void ImportCsvFile(string filename)
{
    FileInfo file = new FileInfo(filename);

    using (OleDbConnection con = 
            new OleDbConnection("Provider=Microsoft.Jet.OLEDB.4.0;Data Source=\"" +
            file.DirectoryName + "\";
            Extended Properties='text;HDR=Yes;FMT=Delimited(,)';"))
    {
        using (OleDbCommand cmd = new OleDbCommand(string.Format
                                  ("SELECT * FROM [{0}]", file.Name), con))
        {
            con.Open();
 
            // Using a DataReader to process the data
            using (OleDbDataReader reader = cmd.ExecuteReader())
            {
                while (reader.Read())
                {
                    // Process the current reader entry...
                }
            }

            // Using a DataTable to process the data
            using (OleDbDataAdapter adp = new OleDbDataAdapter(cmd))
            {
                DataTable tbl = new DataTable("MyTable");
                adp.Fill(tbl);

                foreach (DataRow row in tbl.Rows)
                {
                    // Process the current row...
                }
            }
        }
    }
} 

正如您在示例中看到的,一旦有了 Command 对象,您就可以使用命令对象允许的任何功能。您可以使用 DataReader 对象处理文件,创建一个包含数据的 DataTable 对象,甚至可以在 Command 对象的 CommandText 中添加一个 where 子句来更好地指定要导入的数据。

辅助类

利用这一点,以及本 Microsoft 文章中提供的信息,我创建了一个小型类,允许您导入分隔符文件。该类非常基础,但可以轻松扩展以满足您的特定需求。该类将解决您在使用 Jet 作为导入引擎时遇到的大部分主要问题。

当您导入分隔符文件时(无论使用此类别还是自定义代码),请考虑以下几点

  • Jet 引擎会假设文件的内容。这可能导致导入不正确。例如,它可能认为一列包含日期值。但实际上,您的文件应该将该列视为 string。在这些情况下,您应该创建一个 Schema.Ini 文件来描述每列值的类型。该类在打开分隔符文件之前会创建一个 Schema.Ini 文件,但仅用于指定分隔符是什么。您可能希望将其更改为使用预定义的 INI 文件来描述您的输入文件。有关 Schema.Ini 文件的详细信息可以在 此处找到。
  • 该类使用 OleDbDataReader 来读取导入文件中的每一行。但它很容易被替换为将数据添加到 DataSet DataTable 对象中的选项。也可以使用 SqlBulkCopy 将所有数据立即插入到 SQL Server 数据库中。
  • 上述 Microsoft 文章是此类导入的最佳起点。您可能想在开始构建分隔符文件导入之前阅读它,即使此类别对您有用。该文章提供了有趣的背景信息和指向各种 Microsoft 资源的链接,其中包含更多详细信息和信息。
  • 辅助类使用一个事件来允许您处理正在读取的信息。当然,您也可以提供一个可重写的方法。

宝贵资源

我用来构建此类的信息是在互联网上找到的。我使用了以下资源

免责声明

辅助类中提供的代码并不是一个通用的导入解决方案。它只是一个基础类,用于帮助您构建自己的导入类。如果您需要其他导入类型,或者需要影响默认 Schema.ini 文件内容的方法,您需要自己实现。如果您发现任何问题,请随时指出。

历史

  • 2008年7月15日:初始帖子
© . All rights reserved.