gpt4 book ai didi

delphi - 如何显示长时间过程的 GUI 进度?

转载 作者:行者123 更新时间:2023-12-03 19:07:42 30 4
gpt4 key购买 nike

我需要处理一些数据,每 5-10 秒显示一个进度(我以 % 显示进度,但我也更新了一些图表)。我想在没有多线程的情况下做到这一点。
循环可能相当大。它可以从数百万开始,可以高达数十亿。

我可以使用 GetTickCount:

const 
RefreshEvery= 5000;

for x:= 1 to 10000000000 do
if GetTickCount-OldTime> RefreshEvery then
begin
OldTime:= GetTickCount;
if Assigned(FProgress) then FProgress(Self);
end;

但是在执行数十亿次的循环中调用 GetTickCount ......

关于最有效的方法的任何想法?

为什么没有多线程?
这是一个大型应用程序,在 GUI 进度模块中存在故障。我想解决这个问题,重新打包并交付它,而不需要对其进行需要再次进行密集测试的大改动。多线程?...很酷,但稍后...

最佳答案

您的问题似乎是关于确定评估发布进度更新的间隔的有效方法。如果您对线程方法一无所知,那么您正在做的事情很好 - 改进它的方式并不多。事实上,确定更新间隔的效率在线程代码中也同样重要,因此问题是否线程是相同的。

您似乎对 FProgress(self) 的内容没有问题(即:如何执行状态更新),这似乎也不是关于“解冻”GUI,所以我不会解决这些问题。

你的选择是

  • GetTickCount -- 基于时间更新
  • if x mod 1000 = 0 -- 根据循环变量更新
  • (类似)if x shl 22 = 0 -- 和上面一样,但是一个没有除法的棘手的 mod 1024
  • 根据@LURD,您还可以使用 if i and $3FF = 0 之类的东西类似性能

  • 如果您的循环有任何内容,它们的性能几乎相同。去测试 :
    program Project1;

    uses Windows, SysUtils;

    {$APPTYPE CONSOLE}

    var
    i : integer;
    t0 : cardinal;
    begin
    t0 := GetTickCount;
    for i := 0 to 1000000000 do begin
    if t0 - GetTickCount > 1000 then;
    end;
    t0 := GetTickCount - t0;
    WriteLn('GetTickCount : ' + IntToStr(t0));

    t0 := GetTickCount;
    for i := 0 to 1000000000 do begin
    if i mod 1000 = 0 then;
    end;
    t0 := GetTickCount - t0;
    WriteLn('i mod 1000 : ' + IntToStr(t0));

    t0 := GetTickCount;
    for i := 0 to 1000000000 do begin
    if i shl 22 = 0 then;
    end;
    t0 := GetTickCount - t0;
    WriteLn('i shl 22 : ' + IntToStr(t0));

    ReadLn;
    end.

    产生输出(对我来说)
     GetTickCount : 3978   
    i mod 1000 : 3386
    i shl 22 : 2184

    最后一个选项的性能大约是两倍,但是如果您的循环正在做任何实质性的事情,您可能不会注意到任何差异。

    附录 :

    如果您需要让自己满意,移位是一种准确的方法:
    program Project1;

    uses SysUtils;

    {$APPTYPE CONSOLE}

    var
    i : integer;
    begin
    for i := 0 to 1000000000 do begin
    if (i shl 22 = 0) <> (i mod 1024 = 0) then
    WriteLn('not the same! : ' + IntToStr(i));
    end;
    WriteLn('complete.');
    ReadLn;
    end.

    请注意 i shl 22不等于 i mod 1024 ,但对于 i 的相同值,它们都为零.

    关于delphi - 如何显示长时间过程的 GUI 进度?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25547710/

    30 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com