异常就是 阻止当前方法或作用域继续执行的问题 。当程序运行时出现异常时, 系统会生成一个Exception对象来通知程序进行相应的处理 。
Java将异常当做对象来处理,它的体系结构图如下。
Throwable作为所有异常类的超类,异常分为两大类, Error (错误)和 Exception (异常)。
Error是 程序无法控制和处理 的问题,如栈溢出(StackOverFlowError)、堆溢出(OutOfMemoryError)。
Exception是用户程序可以处理的异常,其下又可以分为 受检异常 (IOException)、 非受检异常 (RuntimeException,也叫运行时异常)。
Java异常处理的本质是 捕获异常 和 抛出异常 。
用法
try{ ///可能会抛出异常的代码` }catch(Type1 id1){ //处理Type1类型异常的代码` }catch(Type2 id2){ //处理Type2类型异常的代码` }finally{ // 回收资源 } 复制代码
try块中放置可能会发生异常的代码,当异常发生, 系统会生成一个异常对象并抛出 。然后异常处理机制将负责 查找catch语句中与该异常类型匹配的第一个处理程序 ,如果找到则执行catch下的处理程序。如果未找到,JVM会抛出该异常。
finally语句块 总是会被执行 ,它主要用来 回收try中的物理资源 。只有finally执行完后,才会回去执行try或catch中的return、throw。如果finally中存在return、throw,那么不会跳回,方法终止。
手动抛出异常,如
throw new Exception() 复制代码
public void f() throws ClassNotFoundException,IOException{} 复制代码
throws关键字常用在方法签名中,当前方法如果不知道如何处理异常,则可以将异常抛给调用者或JVM。JVM对异常的处理方式是 打印堆栈信息并终止程序运行 。
将底层的异常逐层往上抛出,这样每层的异常组合起来就会形成一条链。
try { lowLevelOp(); } catch (LowLevelException le) { throw (HighLevelException) new HighLevelException().initCause(le); } 复制代码
当程序捕获到一个异常,并选择将该异常往上层传递,这样 高层的异常递归调用 getCause()
方法就能拿到各层的异常原因 。