我有一些清理代码,即使我的C#应用程序崩溃(删除临时文件等),我也希望在执行结束时执行。这可以在C#中做到吗?
谢谢!
答案 0 :(得分:9)
这取决于“崩溃”的含义。
如果您想处理任何可能导致应用程序失效的未处理异常,您可以将事件处理程序附加到AppDomain.UnhandledException事件,然后处理事件处理程序中的任何错误。
此外,在.Net 4.0中,在发生异常时执行任何catch块之前会调用AppDomain.FirstChanceException。
然而,可能会发生真正的崩溃(例如从终结器抛出异常)导致致命的应用程序退出无法轻松处理,但在大多数情况下,AppDomain.UnhandledException事件可能就足够了。 / p>
答案 1 :(得分:5)
如果您的应用程序崩溃,那么尝试执行清理代码是不安全的,您不知道什么已损坏,并且在您的应用程序实际退出之前,文件可能被锁定等。
所以我建议你把这个清理代码放在应用程序 startup 上。让你的应用程序在启动之前查找临时文件等,然后创建它的普通临时文件,如果它找到它们,那么它可以删除它们或尝试修复/重用它们。
为方便起见,您可以让应用程序写入它创建的临时文件的日志,并在关闭成功时删除该日志文件。这样,当您在启动时找到日志文件时,您知道上次运行是崩溃,您必须进行清理。
当然,如果您允许多个应用程序实例同时运行,这会变得更加复杂,但同样也可以在崩溃时进行清理。
答案 2 :(得分:2)
您可以订阅几个事件以获取例外通知。
此外,正如其他人所提到的,对于主线程上的任何异常,都会针对单个入口点触发finally块。
[我不建议尝试从这些处理程序中恢复您的应用程序。特别是在AppDomain.UnhandledException事件的情况下,您的应用程序已经开始了,您应该让它关闭。只能使用这些处理程序进行最后一分钟的清理或记录。]
答案 3 :(得分:1)
如果您的应用程序清理至关重要,您可以创建一个用户实际启动的监控应用程序。它将启动您的主应用程序,然后监视其进程句柄。如果您的主应用程序崩溃,其进程句柄将发出信号,您的监视器应用程序可以清理,甚至可以重新启动主应用程序。我通常将它与一个命名的互斥体结合起来,用于向主应用程序希望关闭的监视器应用程序发出信号,以便它不会重新启动它。
答案 4 :(得分:0)
这取决于“崩溃”的含义。如果您指的是未处理的异常,则可以为Application.ThreadException创建一个处理程序。如果崩溃是在托管代码之外引起的,那么你无能为力。
答案 5 :(得分:-3)
这就是try {} finally {}
的用途。将所有代码包含在其中的main
方法中,应该这样做。