TADODataset字段AsString性能

时间:2015-08-28 13:56:35

标签: sql-server delphi ado vcl delphi-2007

我一直在尝试从Delphi程序(使用Delphi 2007)从MSSQL服务器检索数据。 到目前为止,该程序一直使用TADODataset来检索数据。在测试期间,我们发现使用ODBC提供程序的TQuery可以更快地获取大量数据。 但另一方面,TADODataset通过参数化+准备选择预先形成得更好。 TADODataset和TQuery都连接到同一个MSSQL数据库表。对于这个实验,我使用MSSQL Native Client作为两者的提供者。 TADODataset设置了一个到数据库的连接字符串,TQuery使用带有ODBC连接的TDatabase。

以下是实验中的一些代码:

procedure TForm2.Button1Click(Sender: TObject);
begin
  ADODataSet1.CommandText := 'select top 100000 '+FDataFields+' from transactions';
  GetData(ADODataSet1);
  ReadData(ADODataset1);
  ADODataSet1.Close;
end;

procedure TForm2.Button2Click(Sender: TObject);
var
  I: Integer;
begin
  ADODataSet1.CommandText := 'select '+FDataFields+' from transactions where originaltransno = :FieldValue order by Key2';
  ADODataSet1.Parameters[0].Value := '000';
  ADODataSet1.Prepared := True;
  GetData(ADODataSet1);
  for I := 0 to 2000 do
  begin
    ADODataSet1.Parameters[0].Value := '123';
    //no match in DB, just a check if it is there
    ADODataSet1.Requery;
    ReadData(ADODataset1);
  end;
  ADODataSet1.Close;
  ADODataSet1.Prepared := False;
end;

procedure TForm2.Button3Click(Sender: TObject);
begin
  Query1.SQL.Clear;
  Query1.SQL.Add('select top 100000 '+FDataFields+' from transactions');
  GetData(Query1);
  ReadData(Query1);
  Query1.Close;
end;

procedure TForm2.Button4Click(Sender: TObject);
var
  I: Integer;
begin
  Query1.SQL.Clear;
  Query1.SQL.Add('select '+FDataFields+' from transactions where originaltransno = :FieldValue order by Key2');
  Query1.Params[0].Value := '000';
  Query1.Prepare;
  GetData(Query1);
  for I := 0 to 2000 do
  begin
    Query1.Params[0].Value := '123';
    Query1.Close;
    Query1.Open;
    ReadData(Query1);
  end;
  Query1.Close;
  Query1.UnPrepare;
end;

procedure TForm2.GetData(ADataSet: TDataSet);
begin
  ADataSet.DisableControls;
  ADataSet.Open;
end;

procedure TForm2.ReadData(ADataSet: TDataSet);
begin
  while not ADataSet.EOF do
  begin
    ReadLine(ADataSet);
    ADataSet.Next;
  end;
end;

function TForm2.ReadLine(ADataSet: TDataSet): string;
var
  I: Integer;
begin
  for I := 0 to ADataSet.Fields.Count - 1 do
  begin
    if ADataSet.FieldDefs[I].DataType = ftString then
      Result := Result + ADataSet.Fields[I].AsString;
  end;
end;

粗略计时(使用任务管理器中的CPU时间)

  • Button1 - TADODataset大选:13秒
  • Button2 - TADODataset small选择:7秒
  • Button3 - TQuery大选:4秒
  • Button4 - TQuery small选择:24秒

进一步的测试表明,大型TADODataset选择的缓慢时间来自于读取字段AsString 我尝试更换ReadLine:

function TForm2.ReadLine(ADataSet: TDataSet): int64;
var
  I: Integer;
begin
  for I := 0 to ADataSet.Fields.Count - 1 do
  begin
    if ADataSet.FieldDefs[I].DataType = ftInteger then
      Result := Result + ADataSet.Fields[I].AsInteger;
  end;
end;

有了整数读数,我得到了这些时间:

  • Button1 - TADODataset大选:3秒
  • Button3 - TQuery大 选择:3秒

我尝试使用Value,但是"添加"字符串的Variant要慢得多

我可以在读取加速TADODataset读取的字符串时做些什么吗?

0 个答案:

没有答案