一、异常的概念
是一种Java处理程序在运行时而不是编译时的错误机制,出现异常事件的时候会生成异常对象,该异常对象封装了异常事件的信息并将提供给Java运行时系统。
Java的异常类分为可捕获和必须捕获两类,
举给例子,ArithmeticException这个异常,就是RuntimeException下面的,比如程序中除数是0的时候就会抛出这个异常。Error是程序中无法处理的错误,是虚拟机层次的,而Exception是可以在程序中处理的,Exception下面的RuntimeException是可以捕获也可以不捕获的异常,除此之外的异常都是必须捕获的,ArithmeticException异常的继承关系如下图
public class exc {
exc() {
System.out.println(2/0);
}
public static void main(String[] args) {
exc test = new exc();
}
}
编译是没问题的,输出如下:
提示说在main里面有异常发生。System.out.println(2/0);这一句的异常如何捕获:
public class exc {
exc() {
try{
System.out.println(2/0);
}catch (ArithmeticException e) {
System.out.println("除数不能为0");
e.printStackTrace();
}
}
public static void main(String[] args) {
exc test = new exc();
}
}
e.printStackTrace();
这是把堆栈信息打印出来,就是错误的详细信息,不加这一行,输出结果就只有“除数不能为0”
上面的e实际上是一个对象名,有异常发生的时候,会生成异常对象,这个名字是可以随便取的。
二、方法声明和抛出异常
定义一个方法,但是这个方法有可能在运行的时候抛出异常,见下面程序:
public void method() throws SomeException {
if (something) {
throw new SomeException("错误提示");
}
}
在方法名后面用throws关键字声明这个方法有可能会抛出异常, SomeException是举例抛出的异常名字,方法体里面满足某条件以后就用关键字throw来抛出异常。
调用该方法的时候,要捕获异常(当然有些异常是不用捕获的RuntimeException)
try {
method();
}catch (SomeException e) {
//捕获以后的处理代码
}
多个异常,可以一个try多个catch
void f() throws FileNotFoundException , IOException {
FileInputStream in = new FileInputStream("myfile.txt");
int b;
b = in.read();
while (b != -1) {
System.out.print((char) b);
b = in.read();
}
}
void f2() throws IOException {
try {
f();
} catch (FileNotFoundException e) {
System.out.println(e.getMessage());
} catch (IOException e) {
e.printStackTrace();
}
}
当异常发生的时候,程序会终止当前流程,根据捕获的异常类型去执行相应的catch代码段。
三、finally关键字
finally里面的语句是始终都要执行的。
格式类似如下:
try {
method();
}catch (SomeException e) {
//捕获以后的处理代码
}catch (SomeException1 d) {
//捕获以后的处理代码
}finally {
//do something
}
四、注意点
1、多个捕获catch的时候,不能先捕获大的,再捕获小的,比如:
try {
method();
}catch (Exception e) {
//捕获以后的处理代码
}catch (ArrayIndexOutOfBoundsException d) {
//捕获以后的处理代码
}
这里第一次捕获的是Exception,已经包含了所有的异常,下面再捕获数组越界异常,就会报错,因为前者已经包含后者。
2、重写一个方法的时候,原方法所抛出的异常是什么类型,重写以后就必须是抛出什么类型,或者重写以后选择不抛出也可以,如果要抛出,就必须和原方法一模一样。