【问题标题】:Stop application from exiting阻止应用程序退出
【发布时间】:2012-03-27 20:21:05
【问题描述】:

我正在开发一个 Windows 应用程序(不是 WinForms,不是控制台,不是 WinService),只是一个带有入口类的项目。 在 .NET 中,阻止应用程序退出 Main 方法的最佳方法是什么?

我知道我可以在控制台中使用 Console.Read() 来实现这一点,或者我可以使用 EvenWaitHandle.WaitOne() 而从不调用 Set()。

有更好的方法吗?

提前感谢您的帮助。

更新:

这是应用程序的概述。

我需要按需启动包含 wcf 服务的独立进程(一些 exe)。 WCF 服务应该听得很清楚,这就是我需要这个功能的原因。我能找到的最相似的方法是 IIS(许多 w3wp 进程同时运行)。

w3svc.exe(IIS windows 服务)根据配置的应用程序池的数量和它接收的请求启动许多 w3wp.exe 实例。

在我的应用程序中,我想在 IIS 基础结构中保持代表 w3wp.exe 的进程,而不是 w3svc。什么样的消息循环可以让 w3wp 在 .NET 中保持活跃?

【问题讨论】:

  • 应用程序实际上在做什么?你有另一个线程打开做工作吗?如果是这样,请不要将其放在另一个线程中,以便 main 方法在工作完成之前不会结束(即使工作永远不会完成)。
  • @AnuragRanjhan 在 for 循环中多了一个 ;,这些选项比 WaitOneThread.Sleep 更糟糕
  • 没错。我有一个 wcf 服务在上面运行。它不能是 Windows 服务,因为我需要同时运行许多相同的进程 (exe) 并按需启动它们或关闭它们。
  • @Servy 已修复,我同意。只是列出选项:)。
  • 我有一个管理这些进程的 Windows 服务。但除非服务关闭进程,否则进程应继续侦听。关闭进程与完成任何任务没有任何关系。

标签: c# c#-4.0


【解决方案1】:

您可以通过多种方式做到这一点。我个人喜欢这个,因为它非常易读且不言自明:

Process.GetCurrentProcess().WaitForExit();

【讨论】:

    【解决方案2】:

    IIS 是一个 Windows 服务,这就是它运行的原因。您可能会查看其他选项,例如可以通过 api 调用它并告诉它启动另一个线程或侦听器的单个服务。启动新的应用程序实例并不是最好的选择。通常,Windows 应用程序有一个消息泵,我认为这是一个 while 循环......这会阻止它退出。

    不过,你也可以按照这里的例子,我相信不会关闭无形窗口:

    Run Formless Notification User Control?

    【讨论】:

    • 我知道 IIS 是一个 Windows 服务,但并不是您在任务管理器中看到的所有 w3wp.exe 实例。这些都是由 w3svc.exe (IIS) 启动的,我也想达到同样的效果。 w3wp 内部运行着什么样的消息泵?这是真正的问题。
    • 只需使用标准的 Windows 消息泵...它只是一个高效的 while 循环。我相信如果你点击我发布的链接,它就会有你需要做的事情,因为我认为 Windows 窗体只是在顶部运行并隐藏你的泵。
    • 您的链接有意义。让我试试。谢谢
    【解决方案3】:
    while(true)
    {
        // to make it less CPU intensive
        Thread.Sleep(1000);
    }
    

    当然,你能想到的任何解决方案都不会通过杀死进程来阻止应用程序的强制终止。

    【讨论】:

      【解决方案4】:

      在您的更新中,您说该程序正在使用 Process 启动其他几个程序。 (它恰好是“你自己”,但这没关系。)

      如果程序已经完成了它,它听起来就没有更多的事情要做了。该进程结束不会杀死它产生的所有进程。

      您可以使用process.WaitForExit() 等待您生成的进程全部退出,而不是仅仅旋转无所事事,如果出于某种原因您确实需要保持进程处于活动状态。如果在生成其他进程之后它实际上需要做某事,那么您需要告诉我们那是什么,因为如果有什么事情您应该等待某种事件,而这是您没有的事情长大了。

      编辑:您声称所有过程都在“倾听”。定义该任务。如果您有一个阻塞的 GetNextRequest 方法,那么您只需:while(true){GetNextRequest();}。如果它是非阻塞的,则使用BlockingCollection<MyRequests>,其中接收方法/事件处理程序将新项目添加到集合中,并且主线程有一个while循环,就像我在从阻塞集合中读取之前提到的那样。关键是你不应该只是坐在那里什么都不做。您的进程正在做某事,因此请在 while(!done)while(true) 循环中执行此操作。如果该方法没有阻塞,那么这是一个定义合理的问题,需要解决;只需将其包装在阻塞方法调用中即可。

      【讨论】:

      • 同样,这些进程托管 wcf 服务。他们是听众,他们需要无限期地站起来。我不希望他们退出,我希望他们继续倾听。 WaitForExit 在等待什么?一件作品?还是有关闭它的信号?
      • 您说您的程序正在生成其他进程,大概是使用Process 类。如果需要等待,您可以等待这些进程。如果您谈论的是工作进程,而不是产生它们的进程,那么监听方法是否没有阻塞调用?
      • 我想我不是很清楚。我想知道如何永远不退出这些进程(exe)中的每一个的 Main 方法。我不担心程序会产生我的进程,因为它是 Windows 服务,我知道除非我停止 Windows 服务,否则它将永远运行。我很担心那些不是由我的 Windows 服务启动的 Windows 服务,并且我希望它们永远启动,除非我杀死它们。
      • 关键是,如果一个进程什么都不做,只是坐在 Thread.Sleep 中,那么它显然什么都不做,还不如死掉。如果它真的在做某事,我们需要知道你在做什么的细节,以告诉你如何确保它在实际完成之前不会完成。通过忽略整个“它实际上做了什么”部分,您会阻止我们给出任何有意义的答案。
      • 它正在监听调用(WCF 服务主机)。这就是他们正在做的,倾听。由于应用程序要求,我想让所有这些 WCF 侦听器在不同的进程中运行。最简单的问题是:如何在控制台应用程序上运行 ServiceHost 并阻止控制台应用程序到达 Main 方法的末尾,以便您的 ServiceHost 可以永远监听。我知道您有 Console.Read() 用于控制台应用程序。对于不需要在屏幕上显示黑色窗口的更精致的应用程序,您有什么要求?
      【解决方案5】:
      System.Threading.Thread.Sleep(millisenconds);
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2011-04-30
        • 2023-04-01
        • 2012-02-12
        • 1970-01-01
        • 1970-01-01
        • 2014-02-07
        • 2011-02-01
        相关资源
        最近更新 更多