【问题标题】:ADO speed up to open table accessADO 加速打开表访问
【发布时间】:2013-04-16 10:28:24
【问题描述】:

根据写入数据的速度,对于 rs.AddNew 和 rs.Update,使用 ADO 和 Access 打开表的最佳方法是什么?

我需要使用特定的光标或特定的方法吗?

我使用 ADO 连接从 VB6 到 Jet。

【问题讨论】:

  • 这不是一个容易回答的问题,甚至比最天真的“什么是最好的?”还要少。我们在这里看到的问题。有很多变量需要考虑:数据库是共享的还是独占的,你是只使用一个表还是表之间有很多关系,使用模式是什么。

标签: ms-access vb6 ado


【解决方案1】:

我的两个建议是:

  1. adOpenStatic 形式打开记录集,以尽量减少尝试跟踪其他用户可能对表进行的更改的开销。

  2. 通过在批量插入之前执行 cn.BeginTrans 和之后执行 cn.CommitTrans 将多个 .AddNew 操作包装在事务中。

编辑

在回应@Bob77 的评论时,他说:

围绕一系列任意更新操作抛出 Begin/End Trans 不会提供任何内在的性能优势,而且在大多数情况下会使事情变得更糟。

以下 VBScript 测试结果清楚地表明,在使用 Jet/ACE 数据库时,将一批插入包装在 Transaction 中可以大大提高性能。

Option Explicit
Dim con, rst, t0, i, n, s
Const adUseClient = 3
Const adOpenStatic = 3
Const adLockOptimistic = 3
Const useTransaction = False

t0 = Timer
n = 1000
Set con = CreateObject("ADODB.Connection")
con.CursorLocation = adUseClient
con.Open "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=Y:\adoTimeTest.accdb;"
Set rst = CreateObject("ADODB.Recordset")
rst.Open "SELECT * FROM tbl", con, adOpenStatic, adLockOptimistic
If useTransaction Then
    con.BeginTrans
End If
For i = 1 to n
    rst.AddNew
    rst("ItemName").Value = "Item_" & i
    rst("SeqNo").Value = i
    rst.Update
Next
If useTransaction Then
    con.CommitTrans
End If
rst.Close
Set rst = Nothing
con.Close
Set con = Nothing
s = "Added " & n & " rows in " & Round(Timer - t0, 1) & " seconds with"
If Not useTransaction Then
    s = s & "out"
End If
s = s & " transaction."
Wscript.Echo s

表[tbl]的结构是

ID       - AutoNumber, Primary Key
ItemName - Text(255), Indexed (duplicates OK)
SeqNo    - Long Integer, Indexed (no duplicates)

测试 1:useTransaction = False

[tbl] 表为空,并且 .addcb 文件已全新压缩。

Y:\>cscript /nologo adoTimeTest.vbs
Added 1000 rows in 103.9 seconds without transaction.

测试 2:useTransaction = True

[tbl] 表已清空,.addcb 文件已重新压缩。

Y:\>cscript /nologo adoTimeTest.vbs
Added 1000 rows in 4.9 seconds with transaction.

编辑

回应@Bob77 的后续评论:

我会再次尝试打开数据库以进行独占访问。

使用 ODBC 和独占访问的其他测试:

con.Open "Driver={Microsoft Access Driver (*.mdb, *.accdb)};Dbq=Y:\adoTimeTest.accdb;Exclusive=1;Uid=admin;Pwd=;"

测试 3:useTransaction = False

[tbl] 表为空,并且 .addcb 文件已全新压缩。

Y:\>cscript /nologo adoTimeTest.vbs
Added 1000 rows in 26.5 seconds without transaction.

测试 4:useTransaction = True

[tbl] 表已清空,.addcb 文件已重新压缩。

Y:\>cscript /nologo adoTimeTest.vbs
Added 1000 rows in 6.1 seconds with transaction.

【讨论】:

  • 对不起...这里是我的 conn 和我的打开表的代码,你能改变这行的重要部分吗?
  • 设置 RS3 = New ADODB.Recordset RS3.CursorLocation = adUseServer RS3.Open "ASS_MF_EC", CONN, 3, adLockOptimistic, adCmdTable Set CONN = New ADODB.Connection With CONN .ConnectionString = "Provider=Microsoft .Jet.OLEDB.4.0;Data Source=C:\ASS_MF\DATABASE\BMAT.mdb;Persist Security Info=False" .CommandTimeout = 0 .CursorLocation = adUseClient .Open
  • @user1579247 如果您想为您的问题添加一些代码,请单击您问题的标签正下方的edit 链接,然后将代码粘贴到那里。
  • 'code'Set RS3 = New ADODB.Recordset RS3.CursorLocation = adUseServer RS3.Open "ASS_MF_EC", CONN, 3, adLockOptimistic, adCmdTable 'code'
  • @Bob77 我再次更新了我的答案。独占访问缩小了差距,但使用事务仍然会获胜。
猜你喜欢
  • 1970-01-01
  • 2019-01-15
  • 1970-01-01
  • 2010-12-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-07-09
相关资源
最近更新 更多