我有一个包含大量线程的控制台应用程序.有些线程监视某些条件,如果条件为真,则终止程序.这种终止可以在任何时候发生.

我需要一个可以在程序关闭时触发的事件,以便我可以清理所有其他线程,并正确关闭所有文件句柄和连接.我不确定是否有一个已经内置到.NET框架,所以在编写自己的.

我想知道是否有这样的活动:

MyConsoleProgram.OnExit += CleanupBeforeExit;

推荐答案

我不确定我在网上哪里找到了代码,但我现在在我的一个老项目中找到了它.这将允许您在控制台中执行清理代码,例如,当控制台突然关闭或由于关机...

[DllImport("Kernel32")]
private static extern bool SetConsoleCtrlHandler(EventHandler handler, bool add);

private delegate bool EventHandler(CtrlType sig);
static EventHandler _handler;

enum CtrlType
{
  CTRL_C_EVENT = 0,
  CTRL_BREAK_EVENT = 1,
  CTRL_CLOSE_EVENT = 2,
  CTRL_LOGOFF_EVENT = 5,
  CTRL_SHUTDOWN_EVENT = 6
}

private static bool Handler(CtrlType sig)
{
  switch (sig)
  {
      case CtrlType.CTRL_C_EVENT:
      case CtrlType.CTRL_LOGOFF_EVENT:
      case CtrlType.CTRL_SHUTDOWN_EVENT:
      case CtrlType.CTRL_CLOSE_EVENT:
      default:
          return false;
  }
}


static void Main(string[] args)
{
  // Some biolerplate to react to close window event
  _handler += new EventHandler(Handler);
  SetConsoleCtrlHandler(_handler, true);
  ...
}

Update

对于那些不判断 comments 的人来说,这个特定的解决方案似乎在Windows 7上运行良好(或根本不起作用).下面的thread条讨论了这一点

.net相关问答推荐

实体框架核心:Azure容器应用程序的执行超时已过期

Powershell机器令牌组

升级到.NET8后,SignalR(在坞站容器上)网关损坏

.NET 7.0中的UseHttpsRedirection和IIS生产部署

使用 DataDog 收集 OpenTelemetry 跟踪

System.IO.Directory.Exists 在 LINQ 语句中失败,但在 foreach 循环中没有

无法使用 int.Parse 从字符串转换值

为什么(真的吗?)List 实现所有这些接口,而不仅仅是 IList

您如何确定两个 HashSet 是否相等(按值,而不是按引用)?

每 X 秒执行一次指定函数

Silverlight 与 Flex

泛型方法是如何、何时、何地具体化的?

什么是编组?当某些东西被编组时会发生什么?

隐式与显式接口实现

返回 IList 是否比返回 T[] 或 List 更糟糕?

将记录器作为单身人士是一个好习惯吗?

在 C# 中,为什么不能将 List 对象存储在 List 变量中

WebClient.DownloadString 由于编码问题导致字符损坏,但浏览器正常

铸造:(NewType)与对象作为NewType

.NET 桌面应用程序中的 Settings.settings 与 app.config