无法使用VBA中的ADODB更新字段
我的目标是能够从封闭的工作簿中读取和写入单元格值。 我使用ADODB来获取所需的信息。 一个文件是由企业网站生成的,所以在使用实际文件之前我无法更改内容。 该文件是Excel格式。 单元格中没有公式,只是值。 我想从工作表中得到date,string,整数,但是我遇到了一些限制。
我写了示例代码来展示发生了什么事情:
Dim rsConn As ADODB.Connection Dim rsData As ADODB.Recordset Dim strFileName As String Dim strFieldNames As String Dim intValue As Integer strFileName = "C:\Tests\Sample.xlsx" ' Fullpath to a workbook 'strFieldNames = "CInt([Proj_Year]) as [Proj_Year]" 'strFieldNames = "[Proj_Year]" strFieldNames = "*" Set rsConn = New ADODB.Connection With rsConn .ConnectionString = "Data Source=" & strFileName & "; Extended Properties=""Excel 12.0; HDR=YES; "";" .Provider = "Microsoft.ACE.OLEDB.12.0" .Open End With Set rsData = New ADODB.Recordset With rsData .Source = "SELECT " & strFieldNames & " FROM A2:AE500;" ' Sheetname not required .ActiveConnection = rsConn '.CursorType = adOpenKeyset ' Tried this - didn't work '.CursorType = adOpenDynamic ' Tried this - didn't work .CursorType = adOpenStatic .LockType = adLockOptimistic .Open End With With rsData .MoveFirst Do While Not .EOF ' Getting the value intValue = .Fields(0).Value ' Make some crazy modifications of the value intValue = intValue + 10 ' Updating .Fields(0).Value = intValue ' this is place where crash happens ' Move to the next record .MoveNext Loop End With rsData.Close Set rsData = Nothing rsConn.Close Set rsConn = Nothing
以下是示例工作簿的屏幕截图: http : //imgur.com/gRRUs5q
我尝试了几种方法:
-
strFieldNames = "*"
我得到工作表中的所有列。 但司机试图猜测字段types,我不喜欢它,因为它的猜测是错误的。 例如,单元格I3应该是string,但实际上它是adDouble
。 所以阅读可能是好的,但我不能写回string。 我尝试使用IMEX=1
但它没有帮助,试图MAXSCANROWS=1
,Readonly=0
但也没有运气。 我不想触摸Windowsregistry来修改猜测行。 -
strFieldNames = "[Proj_Year]"
我只收到一列,但是我遇到了与1中相同的限制。 -
strFieldNames = "CInt([Proj_Year]) as [Proj_Year]"
我收到我想要的types中所需的列。 但是当我运行我收到的代码时:
字段不能更新
代码: .Fields(0).Value = intValue
在上面的代码中,我一次只能读一条logging。 我试图通过使用GetRows读取所有数据(30列,3000行),然后parsing数组的数据到我自己的类。 在读完所有数据之后,我修改这些数据并一次写回到工作表中一条logging。
我需要做什么才能使这个代码工作?
我通常只使用Connection
对象的Execute
方法。
My Before数据集(这是位于FilePath
variables的文件中的数据):
Field1 Field2 1 a 2 b 3 c 4 d 5 e
我的数据集之后:
Field1 Field2 1 b 2 b 3 c 4 d 5 e
这是为我工作的代码。
Const FilePath As String = "C:\Users\MyComputerName\Desktop\Book1.xlsx" Const ConnStr As String = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" & FilePath & _ ";Extended Properties='Excel 12.0 Xml;HDR=YES';" Public Sub testUpdate() Dim conn As ADODB.Connection: Set conn = New ADODB.Connection With conn .connectionstring = ConnStr .Open .Execute "Update [Sheet1$] set Field2='b' where Field1=1" End With If conn.State = adopenstate Then conn.Close: Set conn = Nothing End Sub
其他一些观察
- 这个
strFileName = "C:\Tests\Sample.xlxs"
似乎不是一个有效的文件名。 所以这可能会让你悲伤 - 数据集的第一行不包含标题,因此使用表单名称
[Sheet1$]
作为例子,我相信默认F1,F2,F3
代表字段名称(F1 = Field1)。 如果您想要两全其美,请使用Sheet AND Range来validation范围:[Sheet1$A1:B10]
。 看到这里更多的细节。