{DCC Warning} W1036 变量'$frame'可能未被初始化?

3
有什么想法,为什么我在Delphi XE中会收到这个警告:
[DCC Warning] Form1.pas(250): W1036 变量 '$frame' 可能未初始化。
procedure TForm1.Action1Execute(Sender: TObject);
var
  Thread: TThread;
begin
  ...
 Thread := TThread.CreateAnonymousThread(
   procedure{Anonymos}()

     procedure ShowLoading(const Show: Boolean);
     begin  /// <-------------            WARNING IS GIVEN FOR THIS LINE (line number 250)
       Thread.Synchronize(Thread,
          procedure{Anonymous}()
          begin
            ...
            Button1.Enabled := not Show;
            ...
          end
        );
     end;

  var
    i: Integer;
  begin
    ShowLoading(true);
    try
      Thread.Synchronize(Thread,
        procedure{Anonymous}()
        begin
          ... // some UI updates
        end
      Thread.Synchronize(Thread,
        procedure{Anonymous}()
        begin
          ... // some UI updates
        end
      );
    finally
      ShowLoading(false);
    end;
  end
  ).NameThread('Some Thread Name');
  Thread.Start;
end;

我的代码中没有名为frame或$ frame的变量。我甚至不确定带有$符号的$ frame如何成为有效标识符。

看起来像编译器的魔法。

PS:当然,真实生活中的xosw具有除Form1,Button1,Action1之外的其他名称。


2
可能在这里Delphi中的匿名方法有所解释,在“变量绑定机制”一节中。但是当我试图理解其含义时,我的头晕眼花。 - LU RD
1个回答

3

在XE2中,此编译器警告不存在。 无论如何,为了让你的方法对编译器更清晰一些,请尝试这样做:

procedure TForm1.Action1Execute(Sender : TObject);
var
  Thread: TThread;
begin
  Thread := TThread.CreateAnonymousThread(
    procedure{Anonymos}()


  Type
    TProcRef = reference to procedure (const Show: Boolean);
  var
    i: Integer;
    ShowLoading : TProcRef;
  begin
    ShowLoading:=
      procedure (const Show: Boolean)
      begin
        Thread.Synchronize(Thread,
          procedure{Anonymous}()
          begin
            // Button1.Enabled := not Show;
          end
        );
     end;

     ShowLoading(true);
    ... // and so on.

更新: 我刚在XE中检查了一下,这确实修复了编译器警告。

我在问题评论中提供的参考资料解释了警告和帧对象。 因此,我猜测XE编译器对ShowLoading创建的帧对象感到困惑。而创建一个明确的引用可以解决警告。

更新2:

以下是我的测试结果,仅供参考:

program Project1;

{$APPTYPE CONSOLE}

{$R *.res}

uses
  Windows,Classes, SysUtils;

procedure Action1Execute;
var
  Thread: TThread;
begin
 Thread := TThread.CreateAnonymousThread(
   procedure{Anonymos}()


  Type
    TProcRef = reference to procedure (const Show: Boolean);
  var
    i: Integer;
    ShowLoading : TProcRef;
  begin
    ShowLoading:=
     procedure (const Show: Boolean)
     begin
       Thread.Synchronize(Thread,
          procedure{Anonymous}()
          begin
            // Button1.Enabled := not Show;
          end
        );
     end;

    ShowLoading(true);
    try
      Thread.Synchronize( Thread,
        procedure{Anonymous}()
        begin
          // some UI updates
        end
      );
      Thread.Synchronize( Thread,
        procedure{Anonymous}()
        begin
          // some UI updates
        end
      );
    finally
      ShowLoading(false);
    end;
  end
  ); //.NameThreadForDebugging('Some Thread Name');

  Thread.Start;
end;

begin
  try
    { TODO -oUser -cConsole Main : Insert code here }
    Action1Execute;
  except
    on E: Exception do
      Writeln(E.ClassName, ': ', E.Message);
  end;
end.

尝试了建议。我的XE不喜欢它:[DCC Fatal Error] program1.dpr(409): F2084 Internal Error: O780 - Gad D Lord
@GadDLord,我已经更新了我的测试答案。在我的XE Update 1上编译正常。 - LU RD
答案已被接受。内部错误与建议的解决方案无关。 - Gad D Lord

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