Can someone tell me what this means..

I ran accesses against a global ADO connection in a number of threads 
such that the accesses would occur simultaneously, or at least would 
overlap (this was a test program just to see if or how ADO would 
handle it), with each thread recording the time it started
and completed and needing to iterate through a large table for the 
sake of taking up some time to cause overlap.

The results showed that the threads would not overlap.
That is, each start time was later than the previous thread's stop 
time.

Here's the Execute procedure that I used:
procedure TTestThread.Execute;
var
~ rst: ADODB_TLB.Recordset;
~ lngAffected: OLEVariant;
~ strName: string;
begin
~ Self.start := Loword(GetTickCount);
~ rst := cnn.Execute('SELECT * FROM Customers;', lngAffected, 
adCmdText);
// Just loop through about 600 records or so (takes ~15ms)
~ while not rst.EOF do
~ begin
~~~ strName := rst.Fields.Item['FirstName'].Value;
~~~ rst.MoveNext;
~ end;
~ rst.Close;
~ Self.stop := Loword(GetTickCount);
end;

Five threads where launched at the same time like this:
procedure TForm1.Button1Click(Sender: TObject);
var
~ thrdAcc: TTestThread;
~ i: integer;
begin
~ ListBox1.AddItem(Format('Button Clicked: %d', [LoWord
(GetTickCount)]), Nil);
~ for i := 1 to 5 do
~ begin
~~~ thrdAcc := TTesthread.Create(True);
~~~ thrdAcc.FreeOnTerminate := True;
~~~ thrdAcc.id := i;
~~~ thrdAcc.OnTerminate := Self.ThreadDone;
//  thrdAcc.cnn := cnn; {if testing using a local copy}
~ end;
~ Listbox1.AddItem(Format('Loop completed: %d', [Loword
(GetTickCount)]), Nil);
end;

procedure TForm1.ThreadDone(Sender: TObject);
var
~ thrd: TTestThread;
begin
~ thrd := Sender as TTestThread;
~ Listbox1.Items.Add(Format('id: %d; start: %d; stop: %d',
~~ [thrd.id, thrd.start, thrd.stop]));
end;

As you may have figured out from the above code, TTestThread is 
defined like this:
type
~ TTestThread = class(TThread)
~ protected
~~~ procedure Execute; override;
~ public
~~~ id: integer;
~~~ start, stop: word;
//  cnn: ADODB_TLB.Connection; // local copy
~ end;

The connection "cnn" is a global variable declared as
var
  cnn: ADODB_TLB.Connection;

The connection is created and opened in FormCreate.
I've opened it as an exclusive connection, but even opening it as a 
shared connection produced the same results.

procedure TForm1.FormCreate(Sender: TObject);
const
STR_CONNECT = 'Provider=Microsoft.Jet.OLEDB.4.0;' +
'Data Source=%s;Mode=Share Deny Read|Share Deny Write;';
var
~ strConnect: string;
begin
~ cnn := ADODB_TLB.CoConnection.Create;
~ strConnect := Format(STR_CONNECT, ['c:\myfile.mdb']);
~ cnn.Open(strConnect, 'Admin', '', adConnectUnspecified);
end;

The "Loop Completed" showed a time about the same as when Thread1 
started.
But the "odd" results I am referring to is that Listbox1 showed that 
Thread2 started only after Thread1 finished, and so on. This is not 
the result I get if I replace the recordset opening -> closing code 
with something simple like Sleep(100). In that case the next thread 
can be seen to start BEFORE the previous thread has completed.

It's great that a single global ADO connection that has been opened 
exclusively can handle accesses from multiple threads without 
breaking.
But it seems to achieve this by "queuing up" the threads by itself.

Any comments?

Ian.

Reply via email to