1 异常
1.1 异常简介
程序运行过程中或者软件检查代码,会出现错误,都称为异常。
1.2 错误分类:
-
语法错误
-
逻辑错误
-
异常
其中,语法错误一般的基础工具都能够帮助程序员解决问题,代码的逻辑错误大多数都是通过软件测试来解决的。异常可以通过java提供的异常类型解决,需要程序员写自定义异常处理方式。
1.3 异常的体系结构
Throwable类是java语言中所有错误或异常的超类。
两个已知子类:
- Error:错误类,相当于绝症,在程序中,java虚拟机内存耗尽或者堆栈溢出都是Error
- Exception:异常类,相当于 感冒 发烧,在Java中,程序运行时却出现了问题,导致程序停止。
- 以RuntimeException为代表的一些类,称为非检查异常,用来表示设计或实现方面的问题。
- 以IOException为代表的一些类,称为检查性异常,所谓检查性异常就是自己的编译器检查代码是否存在异常。如果存在检查性异常,一定必须要先进行处理,才能运行程序。
1.4 检查异常和非检查异常
-
检查异常(Checked Exception):
若系统运行时可能产生的类异常,则必须写出处理异常的代码,否则就不会正常运行,也叫作非运行时异常。
-
非检查异常(Unchecked Exception)
非检查异常也叫作RuntimeException,若系统运行时出现当前异常,可以不必在程序中声明异常处理代码,编译可以通过,叫运行时异常。
1.5 常见异常类型
-
非检查异常
非检查异常 说明 RuntimeException java.lang包下多少异常的父类 ArithmeticException 算数异常 IllegalArgumentException 方法收到非法参数 ArraylndexOutOfBoundsException 数组下标越界异常 NullPointerException 空指针异常 -
检查异常
检查异常 说明 ClassNotFoundException 无法找到想要创建的类文件 IOException IO异常类的父类 EOFException 文件结束 NoSuchMethodException 无法找到方法 IllegalAccessException 对垒的访问被拒绝
1.6 异常是如何产生的
Java是面向对象的编程语言,因此,在Java语言中异常也是作为某种数据类型形式出现的,在当某一个方法出现错误时,运行环境就会创建一个异常类型对象,并且把这个传递给系统,程序员可以利用异常处理机制,把异常进行处理。
2 异常处理机制
在Java程序中,如果出现异常,系统会提示,这时可以选择使用try-catch块进行异常处理,还可以选择回避异常,把异常抛给调用者。
2.1 异常的两种处理方式
2.1.1 第一种
自行处理:可能引用异常的代码封装到try块在,在catch块在进行异常处理。
try-catch语法格式:
try{
容易发生异常的语句
异常促发后,有catch捕获到这个异常,在catch可以进行异常处理
}catch(XXXException e){
e就是捕获到的异常实例,包含了异常信息,并且异常实例自动创建的
可以在catch块中处理异常
XXXException 是异常类型,是Exception的子类
}finally{
释放资源的代码 可选
finnlly块中的语句 最终一定会执行
}
public class DemoException02 {
public static void main(String[] args) {
//读取文件
FileInputStream fis = null;
try {
fis = new FileInputStream("d:\\abc.txt");
} catch (FileNotFoundException e) {
e.printStackTrace();
System.out.println("d:\\abc.txt 这个路径文件不存在");
}
System.out.println(fis);
}
}
2.1.2 第二种
回避异常:在方法声明中,也就是方法名的后面可以使用throws关键字进行异常的声明,潜在的告诉调用者,当前这个方法是有异常的,再由调用者决定是否处理异常。
public class DemoException03 {
public static void driverStr(String driver) throws Exception{
Class.forName(driver);
}
}
public class Test01 {
public static void main(String[] args) {
try {
DemoException03.driverStr("com.myspl.jdbc.Driver");
System.out.println("上面的代码已经完成注册驱动。");
} catch (Exception e){
e.printStackTrace();
}
}
}
2.2 多重catch处理异常
public class DemoException04 {
public static void main(String[] args) {
int[] num = new int[5];
int i = 0;
int j = 8;
try {
while (i<6){
j = j-1;
num[i] = i;
System.out.print(num[i]+"/"+j+"=");
System.out.println(num[i]/j);
i++;
}
}catch (ArrayIndexOutOfBoundsException e){
System.out.println("数组下标越界");
}catch (RuntimeException e1){
System.out.println("除数不能为0");
}finally {
System.out.println("我是finally块");
}
}
}
主要事项:
- 多个catch子句中的异常类型只能从小到大去写
- 一个catch子句在,放入多个异常类型,多个异常类型不能是父类子类关系
}catch (ArrayIndexOutOfBoundsException | ArithmeticException e){
System.out.println("数组下标越界");
}
2.3 throw和throws的区别
- throw位于方法体的内部,可以作为单独语句使用;用于在程序中抛出异常;只能抛出一个异常对象。
- throws必须跟在方法参数列表后面,不能单独使用;用于声明在该方法内抛出了异常;后面跟异常类,而且可以跟多个异常类(同一级别的类)。
3.自定义异常
throw关键字:抛出异常
3.1 使用语法方式
try{
发生异常的语句;
}catch(异常类型 对象名){
throw new 异常类型;
}
3.2 自定义异常使用步骤
- 创建一个类,继承Exception
- 根据需求,提供对应的构造器
- 业务代码判断,符合一定条件,抛出异常
- 调用者去处理当前异常try-catch
public class MyException extends Exception{
public MyException(){}
public MyException(String msg){
super(msg);
}
}
public class Person {
private String name;
private int age;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) throws MyException{
if (age<=0 || age>=150){
throw new MyException("年龄不符合范围!");
}else {
this.age = age;
}
}
public class TestMyException {
public static void main(String[] args) {
Person p = new Person();
try{
p.setAge(-1);
System.out.println(p.getAge());
} catch (MyException e) {
e.printStackTrace();
}
}
}