异常
An exception is an event that occurs during the execution
of a program that disrupts the normal flow of instructions.Java异常都是对象,是Throwable子类的实例
分类
![屏幕快照 2019-01-06 下午3.52.30](Java之总结异常/屏幕快照 2019-01-06 下午3.52.30.png)
- 所有的异常类是从 java.lang.Exception 类继承的子类
- All errors and exceptions extend the Throwable class
- 异常可以被程序处理,而错误不能
- ![屏幕快照 2019-01-06 下午3.56.19](Java之总结异常/屏幕快照 2019-01-06 下午3.56.19.png)
Error
是程序无法处理的错误,表示运行应用程序中较严重问题。
大多数错误与代码编写者执行的操作无关,而表示代码运行时 JVM(Java 虚拟机)出现的问题。
OutOfMemoryError
Virtual MachineError
Exception(异常)
是程序本身可以处理的异常。
Checked vs. Runtime Exceptions
除了RuntimeException及其子类以外,其他的Exception类及其子类都属于可查异常。
####checked:
– could have been caused by something out of your program’s control; must be dealt with by your code, or else program will not compile
####unchecked (runtime):
不可查异常(编译器不要求强制处置的异常):包括运行时异常(RuntimeException与其子类)和错误(Error)。
- – your fault!!
NullPointerException (null references) ArrayIndexOutOfBoundsException - – (probably) could have been avoided by “looking before you leap” in your code (testing for such errors)
- – need not be handled, but will crash program if a non-handled runtime exception is thrown
try-with-resource
正常情况下:
static String readFirstLineFromFileWithFinallyBlock(String path)
throws IOException {
BufferedReader br = new BufferedReader(new FileReader(path));
try {
return br.readLine();
} finally {
if (br != null) br.close();
}
}
JDK7+
static String readFirstLineFromFile(String path) throws IOException {
try (BufferedReader br =
new BufferedReader(new FileReader(path))) {
return br.readLine();
}
}
BufferedReader从Java SE7开始就实现了java.lang.AutoCloseable接口。因为BufferedReader声明在了try-with-resources里面,所以无论try语句是正常结束还是异常结束(比方说BufferedReader.readLine方法抛出一个IOException异常),它都会被关闭。
注意:try-with-resources语句也可以像普通的try语句一样,有catch和finally代码块。在try-with-resources语句中,任何的catch和finally代码块都在所有被声明的资源被关闭后执行。
笔记
- 必须捕获的异常,包括
Exception
及其子类,但不包括RuntimeException
及其子类,这种类型的异常称为Checked Exception。 - 不需要捕获的异常,包括
Error
及其子类,RuntimeException
及其子类。
try-catch-finally
try{
//可能会抛出异常的代码
}
catch(Type1 id1){
//处理Type1类型异常的代码
}
catch(Type2 id2){
//处理Type2类型异常的代码
}
finally{
//总是会执行的代码
}
即使在try或者catch块中使用了return语句,finally子句还是会执行。
那么有什么情况finally子句不会执行呢?
有下面两种情况会导致Java异常的丢失
- finally中重写抛出异常(finally中重写抛出另一种异常会覆盖原来捕捉到的异常)
- 在finally子句中返回(即return)
return和finally
总结
1、不管有没有出现异常,finally块中代码都会执行;
2、当try和catch中有return时,finally仍然会执行;
3、finally是在return后面的表达式运算之后执行的;
对于含有return语句的情况,这里我们可以简单地总结如下:
try语句在返回前,将其他所有的操作执行完,保留好要返回的值,而后转入执行finally中的语句,而后分为以下三种情况:
- 情况一:如果finally中有return语句,则会将try中的return语句“覆盖”掉,直接执行finally中的return语句,得到返回值,这样便无法得到try之前保留好的返回值。
- 情况二:如果finally中没有return语句,也没有改变要返回值,则执行完finally中的语句后,会接着执行try中的return语句,返回之前保留的值。
- 情况三:如果finally中没有return语句,但是改变了要返回的值,这里有点类似与引用传递和值传递的区别,分以下两种情况:
- 1)如果return的数据是基本数据类型或文本字符串,则在finally中对该基本数据的改变不起作用,try中的return语句依然会返回进入finally块之前保留的值。
- 2)如果return的数据是引用数据类型,而在finally中对该引用数据类型的属性值的改变起作用,try中的return语句返回的就是在finally中改变后的该属性的值。
catch & uncatch
- Checked异常继承java.lang.Exception类。Unchecked异常继承自java.lang.RuntimeException类。