将分隔文件 (.csv) 中的行导入 MS-Access 表

Posted

技术标签:

【中文标题】将分隔文件 (.csv) 中的行导入 MS-Access 表【英文标题】:Import rows from delimited file (.cvs) into MS-Access table 【发布时间】:2014-06-19 14:29:42 【问题描述】:

系统背景:我正在使用带有用户界面的 Access 2010 和存储数据库的 Microsoft SQL Server 2008 后端。

问题背景:我实验室的一台机器以 .csv 文件的形式输出结果。这些文件被放置在服务器上的一个文件夹中。目前,结果是手动输入到数据库中的。目标是拥有一个可访问的程序 (VBA),它逐行读取文件中的数据,并将文件的每一行插入到数据库中的特定表中。我被指示让我们 ADO 对象来完成此操作。

进度:我的问题在于尝试读取分隔文件的每一行。我得到了一个参考网站http://msdn.microsoft.com/en-us/library/ms974559.aspx,但是当我尝试实现副标题下的示例那么如何使用 ADO 查询文本文件? 时,我遇到了很多错误,坚持找不到方法特别是在connection.Open。我想获取每一行的值并将它们存储到临时变量中以传递给存储过程。存储过程已经创建,并且插入新记录的过程已经创建。

代码旁注: 该代码是一个较低级别的函数,这意味着它不会一次读取文件夹中的所有 .csv 文件。该函数由更高级别的函数指定一个文件名,该函数将从该文件名读取指定文件的每一行并将其存储在表“tblICPMS”中。以下是在 excel 987654322@ 中打开 .cvs 文件时的示例

这是我的代码:

Public Function ImportICPMS(ThisFileName As String, ThisQueueID As Long, BatchID
As Long, InstrumentName As String, TechId As Long)
On Error GoTo HandleError

Const adOpenStatic = 3
Const adLockOptimistic = 3
Const adCmdText = &H0001

Dim obj_fso As Object
Dim objconnection As connection
Dim objRecordset As Recordset
Dim strpathtotextfile As String

'test if file exists (newpath is a public path to folder)'
Set obj_fso = CreateObject("Scripting.FileSystemObject")
If obj_fso.FileExists(NewPath & "\" & ThisFileName) Then
Else
    Err.Raise vbObjectError + 1000, "MyProjectName.MyObjectName", "file " & ThisFileName & " for " & InstrumentName & " not found" 'if false error is raised
End If

Set objconnection = CreateObject("ADODB.connection") 'create ADO objects'
Set objRecordset = CreateObject("ADODB.recordset")

strpathtotextfile = NewPath & "\" 'path to folder where file resides'

objconnection.Open "Provider=SQLOLEDB.1;Data Source=strpathtotextfile;Extended Properties=;HDR = YES;FMT = Delimited"

objrecordset.Open "SELECT * FROM " & ThisFileName,objconnection, adOpenStatic, adLockOptimistic, adCmdText

Do Until objRecordset.EOF

'I do not know what Wscript.Echo means but I want to save the acquired values into
 temp variables to pass them to a stored procedure that inserts them into the table'

Wscript.Echo objRecordset.Fields.Item("Sample Name")
Wscript.Echo objRecordset.Fields.Item("Date and Time Acquired")
Wscript.Echo objRecordset.Fields.Item("Element Full Name")
Wscript.Echo objRecordset.Fields.Item("Concentration")
Wscript.Echo objRecordset.Fields.Item("Units")

'code to insert rows into table would probably go here'
'code to clear out local objects would go here'

objRecordset.MoveNext

Loop
objRecordset.Close
objconnection.Close

我没有包含其余的代码或存储过程,但如果你们想看的话,我可以。我只想将插入的代码集中在我正在处理的部分上。

【问题讨论】:

Const adCmdText = &H0001 也不断自动更改为 Const adCmdText = &H1 【参考方案1】:

您的方法不存在的问题可能是它没有使用该提供程序正确打开 CSV。 据我所知,SQLOLEDB.1 没有此文本阅读器功能。

试试这个,改变:

objconnection.Open "Provider=SQLOLEDB.1;Data Source=strpathtotextfile;Extended Properties=;HDR = YES;FMT = Delimited"

对此,

objconnection.Open "Provider=Microsoft.Jet.OLEDB.4.0;Data Source=strpathtotextfile;Extended Properties=""Text;HDR=YES;FMT=Delimited"""

更新:注意到声明存在问题:

Dim objconnection As connection
Dim objRecordset As Recordset

应该作为,

Dim objconnection As Object
Dim objRecordset As Object

【讨论】:

感谢您的建议,我切换了它,但仍然收到一个编译错误“未找到方法或数据成员”,其中 connection.open 突出显示 我更正了我的答案,因为我注意到扩展属性没有文本并注意双引号 objconnection.Open还是有问题,不知道object.open是不是可以在VBA中使用的方法? 是的,你可以。您使用的参考是我多年来一直使用的参考。你得到的最新错误是什么? ** 但我刚刚注意到一个问题,它已被声明并将更新答案。我的理论是它没有 open 方法,因为它使用的是 DAO 连接(比 ADO 旧,并且打开方式不同 - 功能较少) 这个问题可能是由于存储在 MS Excel 逗号分隔值文件中的 .csv 文件和 Extended Properties=""Text 会不同造成的吗?【参考方案2】:

这个程序是用Delphi XE2编写的 它读取 cvs 字段并将其放入 ADO 表中

procedure addRowsFromCVS(cvsFileName : string; tblDocumentiRighe: TADOTable);

var
  cvsFileToImport   : TStringlist;
  rowCount          : integer;
  fieldCount        : integer;
  fields            : TStrings;
  fieldValues       : TStrings;

  start             : integer;
  currentFieldName  : string;
  currentFieldValue : string;

begin
  // create memory string list
  cvsFileToImport := TStringlist.create;
  fields          := TStringlist.create;
  fieldValues     := TStringlist.create;

  // load rows from file
  cvsFileToImport.loadFromFile(cvsFileName);

  // split fields row
  split(';', cvsFileToImport[0], fields);

  // first field
  start := 0;

  // for all the rows
  for rowCount := 1 to cvsFileToImport.count - 1 do begin
    // start insert
    tblDocumentiRighe.insert;

    // get field values
    split(';', cvsFileToImport[rowCount], fieldValues);

    // ...
    for fieldCount := start to fieldValues.count - 1 do begin
      currentFieldName  := fields     [fieldCount];
      currentFieldValue := fieldValues[fieldCount];

      if currentFieldValue <> '' then begin
        tblDocumentiRighe.fieldByName(currentFieldName).asString := currentFieldValue;
      end;
    end;

    // post record
    tblDocumentiRighe.post;
  end;

  // free
  fieldValues    .free;
  fields         .free;
  cvsFileToImport.free;
end;

【讨论】:

以上是关于将分隔文件 (.csv) 中的行导入 MS-Access 表的主要内容,如果未能解决你的问题,请参考以下文章

使用 phpMyAdmin 将带有部分数据的制表符分隔的 csv 文件导入 mysql 表

导出CSV文件是以逗号为分隔符的吗?

将数据从csv导入excel

将 CSV 插入 mysql

R 中的 fread 将一个大的 .csv 文件导入为一行的数据框

将 csv 逗号分隔值作为多行导入表中