我们期望程序按照好的方向进行,不过倒霉的事情总会发生。找不到文件,服务器出现故障。那么我们应该在发生状况时
加以处理的代码,未雨绸缪。
一、异常处理的目的:
使用了异常处理即使程序出现了异常,仍然可以正常执行后续流程。如果没有做异常处理,程序会在异常的地终止。
实例代码:
- 未使用异常处理的程序,直接终止
package day18;
public class Playground {
public static void main(String[] args) {
System.out.println("程序开始执行");
int a = 12;
System.out.println(a / 0);
System.out.println("程序执行结束...");
}
}
运行结果.png
- 使用异常处理的程序
package day18;
public class Playground {
public static void main(String[] args) {
try {
System.out.println("程序开始执行...");
int a = 12;
System.out.println(a / 0);
}catch (Exception ex) {
ex.printStackTrace();
}
System.out.println("程序执行结束...");
}
}
运行结果:
运行结果.png
二、解决办法:
将可能出现问题的方法放到try语句中,同时对可能出现的异常进行捕获catch,并对捕获后的异常进行处理。
上面的示例中对 整数除以零这个操作放在了try语句中,并对可能抛出的异常进行了处理。
三、异常(Exception)的继承关系
image.png idea里查看类的继承关系.png异常是一种Exception类型的对象。
四、程序可以捕获异常,那么异常是由谁抛出来的呢?
因为你的程序会调用有风险的方法时,也就是声明有异常的方法,即声明有异常的方法把异常抛出来的
,重点是:那个方法抛出异常,哪个方法捕获异常。
声明有异常的方法使用throws
关键词标识抛出的异常, 方法体内抛出异常使用throw
关键词
代码示例:
package day18;
public class TestException {
// 声明异常的方法
public void takeRisk() throws BadException {
throw new BadException();
}
// 调用可能出现异常的方法
public void crossFingers() {
TestException t = new TestException();
try {
t.takeRisk();
} catch (BadException e) {
e.printStackTrace();
}
}
}
方法可以抓住其他方法抛出的异常,异常总是丢回给调用方。
实际应用: 服务器日志分析
:当程序出现异常的时候,因为程序是从最底层的方法抛出的,需要关注最开始的异常问题。
五、try catch 处理什么样的异常?
RuntimeExcetion
被称为不检查异常。除了RuntimeException,编译器会关注Exception的子类。 大部分的runtime异常是因为程序的逻辑问题(比如数组为空的时候,你取第0号元素的属性值),而不是你无法预测的或防止的方法出现的执行期失败。比如:你无法保证别人的服务一直ok
try catch 是用来处理真正的异常,而不是你程序的逻辑错误。该模块要做的是做恢复的尝试,最差也要打印出有效的错误信息。
常见的非运行时异常:
- IOException
- SQLException
- InterruptedException
- ParseException(解析异常)
六、处理异常的两种方式
- try /catch 语句处理
- 在方法声明位置处使用throws 关键词,将异常抛给上层方法。
七、finally: 无论如何都会执行的部分
当try/catch 其中之一有return语句的时候,会先执行finally里的内容之后再执行return语句。
- finally 内不要写return语句,会覆盖掉try /catch里的return语句
- finally 内修改变量的值是
无效的
代码示例:
package day18;
import javax.sound.midi.MidiSystem;
import javax.sound.midi.MidiUnavailableException;
import javax.sound.midi.Sequencer;
public class TryCatch {
/**
* * @throws MidiUnavailableException if the sequencer is not
* * available due to resource restrictions,
* * or there is no <code>Receiver</code> available by any
* * installed <code>MidiDevice</code>,
* * or no sequencer is installed in the system.
*
*/
public String play() {
try {
Sequencer sequencer = MidiSystem.getSequencer();
System.out.println("1. We got a sequencer");
return "3. game over";
} catch (MidiUnavailableException ex) {
ex.printStackTrace();
return "exception";
} finally {
System.out.println("2. 执行finally语句");
}
}
public static void main(String[] args) {
TryCatch tr = new TryCatch();
String resp = tr.play();
System.out.println(resp);
}
}
执行结果:
image.png
七、方法可以抛出多个异常
八、处理多个异常应遵循:多个catch块里的类型要从小到大排列
不应该将大的异常类放在前面,否则小的异常类根本没有机会执行。
网友评论