如何在长循环中处理消息时最小化开销

lke*_*ler 4 delphi optimization overhead

我的Delphi程序中有一些很长但很简单的循环,它可能循环数百万次并需要几秒钟才能执行.循环内部的代码非常快并且已经过优化.这需要很长时间,因为它已经完成了很多次.

例如:

Screen.Cursor = crHourGlass;
R := FirstRecord;
while R <> nil do begin
  { do something simple with R.Value }
  R := R.NextRecord;
end;
Screen.Cursor := crDefault;
Run Code Online (Sandbox Code Playgroud)

现在我不希望我的程序没有响应,所以我想在循环中添加一个Application.ProcessMessages.但我也希望添加的语句尽可能少地减慢循环速度.

我正在关注一个链表,所以我甚至没有可用的计数变量,如果我想要间隔,则必须添加一个.或者我必须添加一个计时器,但需要最小化时间检查.

我应该如何实现这一点,以尽量减少增加的开销?


结论:

现在,我正在做类似APZ28的回答.

但看起来长期我应该实现某种线程来处理这个问题.感谢您指出这一点,因为我认为Application.ProcessMessages是唯一的方法.

Gre*_*ndt 8

你可以把工作循环放在一个线程中,释放主线程进行GUI循环处理.

  • @lkessler:这不是跳过线程的理由.例如,您可以将循环置于异步调用中(例如使用AsyncCalls,http://andy.jgknet.de/blog/?page_id = 100)并在GUI线程中显示模式进度对话框,可以选择允许取消那个行动.在主线程中编写布尔值并在worker中读取它可以在没有同步的情况下完成,因此根本没有开销.通过互锁增量,工作人员同样可以更新循环计数器而不会真正影响吞吐量. (6认同)
  • @Lieven:从来没有永远使用Application.ProcessMessages来做这类事情 - 除非你竭尽全力阻止它,它会在你的应用程序中产生重入问题.Application.ProcessMessages不是*any*问题的解决方案 - 它只是问题的原因*.而不是使用ProcessMessages来模拟线程(它存在于Delphi 1中,因为没有其他方法),你应该"正确"进行线程化; 用真正的线程).在短期内看起来似乎更多的工作,但Application.ProcessMessages从长远来看会花费更多 - 保证. (5认同)