异常就是导致程序被中断,不能正常执行的意外事件。
异常分类:
- 错误:系统级别的,如系统内部出现错误、内存资源耗尽,错误也可以捕捉到,但是无法处理,程序依旧会终止
- 运行时异常:不是必须要进行显示处理的异常,如除数为0、空指针、数组越界造成的异常,尽量避免该类异常
- 可查异常:必须进行显示处理的异常,如io异常
异常的简单层次图:
自定义异常:
public class MyException extends Exception{ public MyException() {} public MyException(String msg) { super(msg); } }
- 自定义异常必须继承自Throwable或其子类
- 自定义异常和其他异常一样使用
异常的处理:
try catch 语句块捕获异常
try { //可能出现异常的代码 }catch(异常类型 变量) { //异常的处理代码,出现异常时才执行 }finally { //不管是否有异常一定会执行的代码 } c
- catch可以一次性捕获多个异常,通过instanceof判断具体异常类型
- try后可以跟多个catch块,子类异常放前面,父类异常放后面,避免子类异常放在后面时执行不到
- try catch语句块可以多层嵌套使用
throw、throws抛出异常
如果方法可能出现异常,并且不打算处理异常,就用throws向上抛出给调用者,调用者不处理再向上抛出
void f1() throws Exception1,Exception2,...{ //可能出现异常的代码,发生异常向上抛出 } void f2() throws Exception1,Exception2,...{ //code if(...) throw new exception-name();//检测问题,抛出异常 //code }
- throws在方法声明上,throw在方法内部
- throws不代表方法一定会抛出异常,而是表示可能出现的异常
- 执行了throw,就一定抛出了某个异常
- 方法中出现运行时异常时,由系统自动抛出,不用显示throw抛出(em...每个函数都throws一大堆,o((⊙﹏⊙))o.)
异常谜题:
try、catch中由return语句,finally语句中代码会不会执行呢?
如果执行,是先执行return语句还是先执行finally语句块?
public class Test { public static void main(String[] args) { System.out.println( function(5,0) ); } public static int function(int a,int b) { int i=0; try { int c=a/b; return ++i; }catch(ArithmeticException e) { return ++i; }finally{ i=20; //return i; } } }
执行结果:
finally中也有return的情况下:20
finally中return注释掉情况下:1
出现这样的结果是因为执行的时候b=0,在计算c的时候除数为0发生异常,跳过try中的后续代码,进入到catch中,然后执行return语句,i增加为1,创建一个临时变量存储1这个用来返回的值,退出函数之前肯定会退出catch语句,try或catch语句块执行完之后一定会执行finally语句块,i 变为20。如果finally中有return就执行finally中的return,创建一个临时变量存储返回值20,然后结束方法得到20;如果finally中return注释掉,执行catch中return,方法返回之前创建的临时变量的值1,尽管此时i=20。