异常说明

publicvoidf{

任何抽象方法的类。如果你要从一个非接口的类继承,那ว么เ你只能从一个ฐ这样的类中去继

为什么要将某个方法声明为finaທl呢?正如前一章提到的那样,它可以防止其他人重载该

voiddispo色{

importuceeckeltools;

charcນ;

freshsources1้9๗9๗5๓006ahtm此文档的最后部分。

一般说来,如果在一个程序里使用了“直接常量”literal,编译器可以准确地知道要生成

你可以使用多个标签,以便列出所有作者,但是它们必须连续放置。全部作者信息会合并到เ

维护文档的费用。

在某些语言中,你必须明确地声明希๶望某个ฐ方แ法具备后期绑定属性所带来的灵活性cນ++是

prenticehaທll恰当的地点和恰当的时间出现,他将责任转交给paul之前,为这些书๰奠定

但是,掌握好jaທva语言并不是一件可以轻松完成的任务,如何真正掌握java语言,从而

里用打印栈轨迹stacktraທce的方法来“修补”这个问题本章中ณ的很多例子还是使

用了这个方法,看起来还是比较合适的。虽然这样可以跟踪异常的行为,但是你仍旧

不知道该如何处理异常。这一节,我们来研究一下“被检查的异常”及其并症,以及

采用什么เ方法来解决这些问题。

这个ฐ话题看起来简单,但实际上它不仅复杂,更重要的是还非常多变。总有人会顽ื固地

坚持自己้的立场,声称正确也是他们的答案是显而易见的。我觉得之所以会有这种

观点,是因为ฦ我们使用的工具已๐经不是“aທnsi标准出台前的c那样的”弱类型语言

poorly-typed浪uage,而是像c++ใ和jaທva这样的“强静态类型语言”strong

stati9๗guage,也就是编译时就做类型检查的语言,这是前者无຀法比拟

的。当你刚开始这个转变的时候就像我一样,会现它带来的好处是那样的明显,

好像强类型检查总能解决所有的问题。在此,我想结合我自己的认识过程,告诉你我是

怎样从对类型检查的绝对迷信变成怀疑ທ的;当然,很多时候它还是非常有用的,但是当

它挡住我们的去路并成为障碍的时候,我们就得跨过去。只是这条界ศ限往往并不是很清

晰。我最喜欢的一句格言是:“所有模型都是错误的。但有些是能用的。”

历史

异常处理起源于pl1和mesa之类的系统中ณ,后来又出现在clu,smalltalk,

摸dula-3๑,adaທ,eiffel,9,javaທ以及javaທ后面的rubຘy和c#中。jaທvaທ

的设计和c++很相似,只是java的设计者去掉了一些他们认为ฦc++设计得不好的东西。

为了能向程序员一个ฐ他们更愿意使用的错误处理和恢复的框架,异常处理机制ๆ很晚

才被加入cນ++标准化过程中,这个ฐ倡议是由9est肉strup所起的。

cນ++的异常模型主要借鉴了clu的作法。然而,当时其他语言已经支持异常处理了:包

括aທdaທ,smalltalk两者都有异常处理,但是都没有异常说明,以及摸dula-3它

既有异常处理也๣有异常说明。

liov和snyder在他们有关异常的开创性论文

5

中指出,用9t

fashion报告错误的语言有一个ฐ主ว要缺陷,就是:

“…每次调用的时候都必须执行条件测试,以确定会产生何种结果。这使程序难以阅读,

并且有可能降低运行效率,因此程序员们既不愿意指出,也不愿意处理意外情况。”

5

barbຘaraliov和aທlansnyder:9dlingin9๗sonsoft9are

engineering,vol色-ๅ5,no6๔,19๗79年1้1้月。这篇论文在网上是找不到เ的,只有印刷版本,所以你得去图

书๰馆找一个ฐ副本。

注意,异常处理的初衷是要消除这种限制,但是我们又从javaທ的“被检查的异常”上

看到เ了这种代码。他们继续写道:

“…在调用会引异常的函数的同时,还要求程序员给出异常处理程序,这会降低程序

的可读性,使得程序的正常思路被异常处理给破坏了。”

cນ++异常的设计参考了clu方式。st肉strup声称其目标是减少恢复错误所需的代码。

我想他这话是说给那些“通常情况下都不写c的错误处理”的程序员们听的,因为ฦ要把

那么เ多代码放到那么多地方实在不是什么好差事。所以他们写c程序的习惯是,忽略所

有的错误,然后使用调试器来跟踪错误。这些程序员知道,使用异常就意味着他们要写

一些通常不用写的“多出来的”代码。因此,要把他们拉到เ“使用错误处理”的正轨上,

“多出来的”代码决不能太多。我认为,评价javaທ的“被检查的异常”的时候,这一点

是很重要的。

c++还从cນlu那ว里还带来另一种思想:异常说明。这样就可以用编程的方式在方法签名

中ณ声明这个方แ法可能会抛出哪些异常。异常说明可能有两种意思。一个是“我的代码会

产生这种异常,你得处理”。另一个是“我的代码忽略了这些异常,它要由á你来处理”。

学习异常处理的机制ๆ和语法的时候,我们一直在关注“你来处理”的部分,但这里特别

值得注意的事实是,我们通常都忽略了异常说明所表达的含义。

c+ใ+的异常说明不属于函数的类型信息。编译时唯一要检查的是异常说明是不是前๩后一

致;比如,如果一个ฐ函数或方法会抛出某些异常,那么它的重载版本或者派生版本也必

须ี抛出同样的异常。与java不同,c+ใ+不会在编译时进行检查以确定函数或方แ法是不是

真的抛出异常,或者异常说明是不是完整也就是说,异常说明有没有精确描述所有可

能被抛出的异常。这样的检查只生在运行期间。如果抛出的异常与异常说明不符,

9๗expecນted函数。

值得注意的是,由于使用了模板template,c++的标准类库实现里根本没有使用

异常说明。由此看来,异常说明会对java的泛型generics产生非常重大的影响jaທva

里面对应c++ใ模板的功能,可望在jdk15๓中出现。

观点

先,java无谓地明了“被检查的异常”很明显是受c++异常说明的启,以及

c+ใ+程序员们一般对此无动于衷的事实。这还只是一次尝试,目前๩为止还没有别ี的语

言采用这种做法。

第二,仅从示意性的例子和小程序来看,“被检查的异常”好处很明显。但是当程序开

始变大的时候,就会带来一些微妙的问题๤。当然,程序不是一下就变大的,这有个过程。