Delphi,在TcxGrid或TDataSet中,最快的记录访问方法是什么?

3
我正在使用Delphi 2007和TcxGrid来显示文件库的内容。数据库包含有关文件类型、名称、路径和扩展名的信息。
在测试中,我通过TDataSet将1700条记录加载到网格中。我还在网格中腾出了3个需要计算的字段。它们是文件是否存在、文件大小和修改日期。
我的目标是向用户显示所有存储的信息(已经很好地实现并且速度很快),然后在后台线程中查找另外三个数据字段的信息,并将它们插入到TcxGrid中。这个问题与我正在进行的线程几乎没有任何关系。它工作得很好。
我的问题是,当我访问已经构建的网格中的字段时,速度非常慢。我尝试了两种不同的方法...
1. Grid.DataController.Values [RecordIndex, FieldIndex] - 但这是一个变量,我怀疑这就是它速度缓慢的原因。
2. Grid.DataController.DataSet.FindFirst Grid.DataController.DataSet.FindNext Grid.DataController.DataSet.Fields[FieldIndex] 但使用这种“查找”方法的速度与我尝试过的第一种方法一样慢。定位和移动方法也很慢。
因此,简而言之,访问记录的最快方法是什么?

2
你进行过性能分析吗?你是否将每个更新操作放在 Begin-EndUpdate 之间?你是否将每个更新操作放在 Enable-DisableControls 之间? - Lieven Keersmaekers
这实际上有多慢啊。对于1700条记录,它不应该需要超过几毫秒的时间。 - Gad D Lord
4个回答

2
请说明您使用的是TcxGridDBTableView还是TcxGridTableView?
我认为使用非数据库感知的TcxGridTableView或TcxBandedGridTableView,并使用View.DataController.Values[RecordIndex, FieldIndex]会更快。
即使您有一个数据库应用程序,您也可以在初始化时加载非数据库版本的视图,然后处理DataController事件以检测数据更改并发出相应的SQL命令来更新数据库。
您可以像这样填充视图:
class procedure TForm1.FillView(const View: TcxGridBandedTableView; const Sql: string);
var
  Reader: TMyOrmDataReader;
  i: Integer;
begin
  Assert(Assigned(View), 'View is not assigned parameter.');
  with View.DataController do
  begin
    BeginFullUpdate;
    try
      Reader := TMyOrm.GetDataReader(SQL);
      try
        i := 0;
        RecordCount := 50 * 1000; // make it something big in order to avoid constant resizing by 1
        while Reader.Read do
        begin
          // Fill the view
         Values[i,  0] := Reader.GetInt32(0);
         Values[i,  1] := Reader.GetString(1);
         Inc(i);
        end;
        RecordCount := i - 1;
      finally
        Reader.Free;
      end;
    finally
      EndFullUpdate;
    end;
  end;
end;

然后像这样访问值:

View1.DataController.Values[View1.DataController.FocusedRecordIndex, View1Column1.Index].AsString

1

我知道这是一个旧的帖子,但我想提到另一种提高加载速度的方法,那就是将网格切换到使用提供程序模式。因为它本质上将网格加载转换为虚拟操作。(记录直到需要显示或其他数据访问时才被加载。)之后,DataController会缓存它们,因此一旦加载,访问非常快。


1

您可以先使用表/数据集进行工作,将缺失的数据添加到其中,然后将所有字段显示为数据绑定。


1

我的一个大问题是需要将更新的代码放在begin/end update之内。

感谢Lieven的评论,它解决了我的问题。还要感谢Gad和Daniel的回复,我从中学到了东西。

如果昨天我有更多时间发布一些代码,这对每个人来说会更加明显。


好的,知道了。谢谢您与我们分享结果。 - Lieven Keersmaekers

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接