代码之家  ›  专栏  ›  技术社区  ›  Jerry Dodge

在新的服务应用程序中,如果没有括号,这条“if not”语句如何工作?

  •  -1
  • Jerry Dodge  · 技术社区  · 6 年前

    在Delphi中创建新的Windows服务时,它将插入以下内容:

    if not Application.DelayInitialize or Application.Installing then
      Application.Initialize;
    

    作者没有费心把括号括起来,所以我想把我的头绕在这上面。翻译为:

    if (not Application.DelayInitialize) or Application.Installing then
      Application.Initialize;
    

    据我所知,如果两者都是 Application.DelayInitialize Application.Installing True ,然后继续 Initialize 服务应用程序。我不明白 为什么 它将在这个场景中被初始化——我很确定它不应该被初始化。

    有人能给我解释一下我在看什么吗?


    在旁注中,我永远不需要启用 DelayInitialize 因为不需要关心Server2003。我只是想了解一下这段代码实际上是什么意思,它的编写方式。

    1 回复  |  直到 6 年前
        1
  •  2
  •   Sertac Akyuz    6 年前

    正如在创建服务应用程序时插入到项目源中的注释所解释的那样, DelayInitialize 存在的特定原因:调用的要求 StartServiceCtrlDispatcher 之前 CoRegisterClassObject . 我想,你是否需要设置它取决于你是否需要打电话 coregisterclassobject项目 ,如果您的目标服务器不是2003,则不会。 (*) . 哎呀,我可不希望每一个新的服务器版本都会更新这个评论。YMMV,可能需要测试。

    这里隐含的设计是你使用的 System.InitProc 打电话 coregisterclassobject项目 (**) ,类似于 CoInitializeEx 呼叫由comobj.pas发出。 InitProc 被称为 Vcl.Forms.Application.Initialize 从哪来的 Vcl.SvcMgr.TServiceApplication.Initialize .

    现在,什么时候 Vcl.SvcMgr.TServiceApplication.Installing 返回真值,这意味着 启动服务控制器分配程序 不会被召唤。因为主线程不会连接到服务控制管理器。相反,它将安装或卸载服务,然后退出。然后,对任何延迟初始化的需求将变为无效,实际上,由于没有运行任何服务线程,因此无法运行延迟初始化。 (***) .

    这就是为什么表达式是这样写的,没有忘记/遗漏的括号。


    (*)d2007有注释,2003 r2是最后一个服务器。

    (**)来自项目来源的评论:

    Windows 2003服务器要求在coregisterClassObject之前调用StartServiceCtrlDispatcher,而coregisterClassObject可以由application.initialize间接调用。

    (***)这是调用延迟初始化的地方,如果可执行文件中有多个服务,则由标志保护。