What is the best method to open a table with ADO and Access, for rs.AddNew and rs.Update, based on the speed for writing data?
Do I need to use a particular cursor or a particular method?
I use an ADO connection to Jet from VB6.
What is the best method to open a table with ADO and Access, for rs.AddNew and rs.Update, based on the speed for writing data?
Do I need to use a particular cursor or a particular method?
I use an ADO connection to Jet from VB6.
My two suggestions would be:
Open the Recordset as adOpenStatic
to minimize the overhead of trying to keep track of changes to the table that might be made by other users.
Wrap multiple .AddNew
operations in a transaction by doing cn.BeginTrans
before the batch of inserts, and cn.CommitTrans
afterwards.
In response to the comment from @Bob77, in which he said:
Throwing Begin/End Trans around a series of arbitrary update operations doesn't provide any intrinsic performance benefit, and in most cases should make matters worse.
The following VBScript test results clearly show that wrapping a batch of insertions in a Transaction can greatly improve performance when working with Jet/ACE databases.
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
The structure of the table [tbl] is
ID - AutoNumber, Primary Key
ItemName - Text(255), Indexed (duplicates OK)
SeqNo - Long Integer, Indexed (no duplicates)
Test 1: useTransaction = False
The [tbl] table is empty and the .addcb file has been freshly compacted.
Y:\>cscript /nologo adoTimeTest.vbs
Added 1000 rows in 103.9 seconds without transaction.
Test 2: useTransaction = True
The [tbl] table has been emptied and the .addcb file has been freshly compacted again.
Y:\>cscript /nologo adoTimeTest.vbs
Added 1000 rows in 4.9 seconds with transaction.
In response to the follow-up comment from @Bob77:
I'd try again opening the database for exclusive access.
Additional tests using ODBC and Exclusive access:
con.Open "Driver={Microsoft Access Driver (*.mdb, *.accdb)};Dbq=Y:\adoTimeTest.accdb;Exclusive=1;Uid=admin;Pwd=;"
Test 3: useTransaction = False
The [tbl] table is empty and the .addcb file has been freshly compacted.
Y:\>cscript /nologo adoTimeTest.vbs
Added 1000 rows in 26.5 seconds without transaction.
Test 4: useTransaction = True
The [tbl] table has been emptied and the .addcb file has been freshly compacted again.
Y:\>cscript /nologo adoTimeTest.vbs
Added 1000 rows in 6.1 seconds with transaction.