一、异常是什么?
异常就是程序出现了不正常的情况。估计没有人敢说自己写的代码完全没有bug,所以在一些可能出现异常的地方,需要对它进行控制,能按照安排好的流程去执行,从而最大程度上避免不可控的情况发生。
注意:异常是Exception类,是可以被我们捕获的。错误是Error类,错误一般发生在严重故障时,它们在Java程序处理的范畴之外
两者的父类是Throwable类
二、异常
1.JVM默认处理异常的方式
a.把异常的名称,错误原因以及异常出现的位置等信息输出在控制台
(这些都是由java内置的异常类进行操作的)
b.程序停止执行
(编译时异常
2.异常概述
首先,异常处理的两大组成要素是抛出异常和捕获异常。这两大要素共同实现程序控制流的非正常转移,是处理程序处于非预期状态的方式
抛出异常:
分为显示抛出和隐式抛出:
1.显示抛出是:在程序中通过关键字“throw”来抛出,能被你看到,手动创建一个异常的实例对象
2.隐式抛出:由JVM来执行,当碰到无法执行的异常状态时,会自动去创建异常类。
捕获异常
捕获异常主要由下面三种代码块进行完成:
格式:
try{
可能出现异常的代码块;
}catch(异常类名 变量名){
异常的处理代码;
}finally{
最后执行的代码
}
try代码块:可能出现异常代码放到这个里面。
catch代码块:和try代码块一起使用,可以捕获try中的异常。catch代码块会定义异常的类型(父类是Exception ),只有当try中的异常类型和catch中的异常类型一致或catch中的异常类型范围更大时,才会执行catch中的代码。catch后面还可以跟catch代码块,但是定义的异常类型范围需要比前面的更大,否则没有意义且会报错。
finally 代码块:跟在try,catch代码块后面,表示这段代码一定会执行。通常用于一些系统资源因为异常程序停止,资源没有关闭而导致资源浪费。
(注意事项:
a.当finally代码块里存在return语句时,try或者catch代码块里的return语句将会被覆盖掉。
b.当finally代码块里没有return语句时,try或者catch代码块里有return语句的话。会先执行try或者catch中其他语句,然后执行finally代码块中的语句,最后再执行try或者catch中的return语句
c.由b可只,finally会比try或者catch代码块中的return语句先执行,也就意味着finally代码块可以对返回值进行修改。但是只能修改引用数据类型,不能修改基本数据类型)
3.编译时异常和运行时异常
a.编译时异常:
是Exception类及其子类
必须显示处理,否则程序就会发生错误,无法编译
b.运行时异常:
是RunTimeException类及其子类
无需显示处理,也可以和编译时异常一样处理
(打个不恰当的比喻,就好比组装一辆汽车一样。编译时异常就是组装汽车时,有没有缺少什么配件,各个配件之间能不能连接好。运行时异常,就是车子组装完好,但是你开上路时也有可能会有故障。
4.throws和throw的区别
1.throws 用来声明一个方法可能抛出的所有异常信息,throw 则是指拋出的一个具体的异常类型。
2.通常在一个方法(类)的声明处通过 throws 声明方法(类)可能拋出的异常信息,而在方法(类)内部通过 throw 声明一个具体的异常信息。
3.throws 通常不用显示地捕获异常,可由系统自动将所有捕获的异常信息抛给上级方法; throw 则需要用户自己捕获相关的异常,而后再对其进行相关包装,最后将包装后的异常信息抛出。
4.自定义异常类
java提供的异常类非常有限,平时会碰到很多的异常,这时候就需要自己去定义一个异常类来满足自己的需求。
编写自己的异常类时需要记住下面的几点:
1.所有异常都必须是 Throwable 的子类。
2.如果希望写一个编译时异常类,则需要继承 Exception 类。
3.如果你想写一个运行时异常类,那么需要继承 RuntimeException 类。
举例:当传入的参数不在范围时,不能创建对象,抛出异常
自定义异常类
class DrinkNotFoundException extends Exception{
String message ;
public DrinkNotFoundException(String message) {
super(message);
this.message = message;
}
}
饮料类里面声明异常方法
class Drink{
//每个常量代表一种饮料
int a = 1;//咖啡
int b = 2;//啤酒
int c = 3;//牛奶
public static void getDrink(int drinkType) throws DrinkNotFoundException {
if (drinkType!=1&&drinkType!=2&&drinkType!=3){
throw new DrinkNotFoundException("没有对应的饮料类型");//后面不能再有语句
}
}
}
测试类来捕获处理异常
class DinkTest{
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int i = scanner.nextInt();
try{
Drink.getDrink(i);
}catch (DrinkNotFoundException e){
e.printStackTrace();
}
}
}
输入6