什么是.NET中的ApplicationException?

Jam*_*mes 162 .net c# exception-handling exception

为了抛出异常,我通常使用内置的异常类,例如ArgumentNullException和NotSupportedException.但是,有时我需要使用自定义异常,在这种情况下我写:

class SlippedOnABananaException : Exception { }
class ChokedOnAnAppleException : Exception { }
Run Code Online (Sandbox Code Playgroud)

等等.然后我在我的代码中抛出并捕获它们.但今天我遇到了ApplicationException全班 - 我应该使用它吗?这是为了什么?

拥有许多具有不同名称的有效相同的异常类似乎效率低下(我通常不需要任何单独的功能).但我不喜欢捕获泛型ApplicationException并且必须使用额外代码来确定错误是什么的想法.

哪里应该ApplicationException适合我的代码?

Qui*_*ith 138

简短的回答是:无处可去.

它是过去的遗留物,Microsoft希望开发人员从ApplicationException继承所有自定义异常.不久之后,他们改变主意,并建议自定义异常应该来自基本的Exception类.请参阅在MSDN上处理异常的最佳实践.

其中一个更为广为流传的原因来自Jeffery Richter在框架设计指南中的一个例外:

System.ApplicationException是一个不应该是.NET Framework一部分的类.最初的想法是从SystemException派生的类将指示从CLR(或系统)本身抛出的异常,而非CLR异常将从ApplicationException派生.但是,很多异常类都没有遵循这种模式.例如,TargetInvocationException(由CLR抛出)是从ApplicationException派生的.因此,ApplicationException类失去了所有意义.从这个基类派生的原因是允许调用堆栈上方的某些代码捕获基类.不再可能捕获所有应用程序异常.

所以你有它.执行摘要是ApplicationException没有害处,只是没用.

  • 顺便说一句,从这个解释看来,这本身并不是一个糟糕的设计,但MSFT搞砸了实现.还有其他人这样看过吗? (8认同)
  • @JoshKodroff:我认为问题是如果应用程序`Whizbang`决定它想要在一些公共层次结构下拥有所有异常,那么为此目的使用`ApplicationException`实际上没有优于使用自定义`WhizbangException`基类.然而,.net的异常层次结构中更严重的问题不是使用`ApplicationException`,而是因为无法将异常分为可能应用程序致命的,可能是线程致命的和本地问题相关的类别,以及无法获得有意义的"复合"例外. (7认同)
  • 有谁知道*为什么*那​​是什么?它似乎有意义,因此您可以显示应用程序异常,但不能显示"程序员搞砸"异常. (2认同)
  • @JoshKodroff还有另一件事令我惊讶的是没有得到更多的关注。真正的“应用程序”是什么?第三方_libraries_呢?由于这些不是.Net框架的一部分,因此应按照原始准则从ApplicationException继承。现在,当您在应用程序中使用该库并创建自己的ApplicationExceptions时,您将无法再基于该库从库的异常中识别出自己的异常。所以这没用。相反,每个组件都应仅定义其自己的异常基本类型,如supercat所述。 (2认同)

Fem*_*ref 92

根据msdn 的评论:

用户应用程序(而不是公共语言运行库)抛出从ApplicationException类派生的自定义异常.ApplicationException类区分应用程序定义的异常与系统定义的异常.

如果您正在设计需要创建自己的异常的应用程序,建议您从Exception类派生自定义异常.最初认为自定义异常应该来自ApplicationException类; 然而,在实践中,尚未发现这增加了重要价值.有关更多信息,请参阅处理异常的最佳实践.

从中获取它们Exception.此外,只要有必要,我认为为您的案例创建新的例外没有问题.如果您遇到框架中已经存在异常的情况,请使用它,否则,请自行滚动.

  • 所以看起来`ApplicationException`是无用的,只是因为向后兼容? (7认同)

aba*_*hev 19

在最初的设计中,在.NET 1.0中,计划框架本身将抛出SystemException并派生; 用户应用程序 - 将抛出ApplicationException和派生.

但后来,在.NET 2.0中,它被删除了.

因此得出Exception.