提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档
文章目录
- 前言
- 1.异常的基本语法
- 关键字及其解释
- 2.简单示例
- 1.数组下标超出限定
- 2.多个异常如何书写
- 3.使用try回收资源
- 3.异常的处理流程
- 简单的实例
前言
两种防御式编程方式:
1.LBYL(look Before You leap) 在操作之前做充足的检查。
2.EAFP(It’s Easier to AsK Forgiveness than Permission) 先操作,遇到问题再处理。
1.异常的基本语法
try{
有可能出现异常的语句 ;
}
[catch (异常类型 异常对象) {
} … ]//这里可以有多个catch
finally {
异常的出口
}
关键字及其解释
try 代码块中放的是可能出现异常的代码.
catch 代码块中放的是出现异常后的处理行为.
finally 代码块中的代码用于处理善后工作, 会在最后执行.
其中 catch 和 finally 都可以根据情况选择加或者不加.
2.简单示例
1.数组下标超出限定
public class Catch {
public static void main(String[] args) {
int[] ar={1,2,3,4,5};
try{
System.out.println(ar[0]);
System.out.println(ar[ar.length]);
}catch(ArrayIndexOutOfBoundsException e){
e.printStackTrace();
}
finally {
System.out.println("完成");
}
}
}
如果不捕获异常,执行到错误代码,就会程序终止,不会执行到下面的代码。在上述代码中,ArrayIndexOutOfBoundsException,这个是出现的异常类,这里因为知道会出现数组下标异常的情况,所以用的是这个类,那么如何知道会出现的异常,及时捕获呢?
(可以先运行一下,方法比较垃圾)因为catch只能处理对应种类的异常,若是没有捕获到,也不会正常结束的,后面的代码也就执行不到了。
调用栈,方法之间是存在相互调用关系的, 这种调用关系我们可以用 “调用栈” 来描述. 在 JVM 中有一块内存空间称为 “虚拟机栈” 专门存储方法之间的调用关系. 当代码中出现异常的时候, 我们就可以使用e.printStackTrace(); 的方式查看出现异常代码的调用栈.
2.多个异常如何书写
package Exception;
public class Catch {
public static void main(String[] args) {
int[] ar={1,2,3,4,5};
try{
System.out.println(ar[0]);
ar=null;
System.out.println(ar[ar.length]);
}catch(ArrayIndexOutOfBoundsException e){
e.printStackTrace();
}catch (NullPointerException e){
e.printStackTrace();
}
// catch (ArrayIndexOutOfBoundsException | NullPointerException e){
// e.printStackTrace();
// }
finally {
System.out.println("完成");
}
System.out.println("主程序结束");
}
}
可以看到有两种写法
3.使用try回收资源
import java.util.Scanner;
public class Catch {
public static void main(String[] args) {
Scanner scanner=new Scanner(System.in);
try{
int num=scanner.nextInt();
System.out.println("num"+num);
}catch (Exception e){
e.printStackTrace();
}finally {
System.out.println("回收资源");
scanner.close();
}
System.out.println("主程序结束");
}
在idea中比较智能,光标放在try上(alt+enter)就会改变上述代码,变成另外一种形式,如下
try (Scanner scanner = new Scanner(System.in)) {
int num = scanner.nextInt();
System.out.println("num" + num);
} catch (Exception e) {
e.printStackTrace();
} finally {
System.out.println("回收资源");
}
3.异常的处理流程
程序先执行 try 中的代码,如果 try 中的代码出现异常, 就会结束 try 中的代码, 看和 catch 中的异常类型是否匹配. 如果找到匹配的异常类型, 就会执行 catch 中的代码
如果没有找到匹配的异常类型, 就会将异常向上传递到上层调用者.
无论是否找到匹配的异常类型, finally 中的代码都会被执行到(在该方法结束之前执行).
如果上层调用者也没有处理的了异常, 就继续向上传递.
一直到 main 方法也没有合适的代码处理异常, 就会交给 JVM 来进行处理, 此时程序就会异常终止
简单的实例
public static void main(String[] args) {
int[] ar={1,2,3,4,5};
try{
func(ar);
}catch(ArrayIndexOutOfBoundsException e){
e.printStackTrace();
}finally {
System.out.println("完成");
}
System.out.println("主程序结束");
}
public static void func(int[] ar){
System.out.println(ar[ar.length]);
}
这里func函数中出现异常,没有处理,就回将异常向上传递到主函数,主函数因为有处理,就会执行catch中的代码,执行结果如下图:
可以看出,此时程序执行完了,且是正常结束的。