前言
在Java语言中,将程序执行中发生的不正常情况称为“异常”。
注:在开发中的语法错误和逻辑错误不是异常。
一、异常事件的分类
在Java程序的执行过程中发生的异常事件总体上可以分成两类
1.1 Error
Java虚拟机无法解决的严重问题
如:Java虚拟机运行错误、Java虚拟机内存不足错误、资源耗尽等
1.2 Exception
其他编程原因或偶然的外在因素导致的一般性问题,可以使用针对性的代码进行处理
二、异常分类
大体上可以分成两大类:编译时异常和运行时异常
2.1 编译时异常
编译时异常是指编译器必须要处置的异常,机程序在运行是由于外界因素造成的一般性异常
2.2 运行时异常
运行时异常是指编译器不要求强制处理的异常,一般是指在编译时的逻辑错误。
注:对于这类的异常,可以不做处理,因为这种异常很普遍。
三、常见异常
3.1 NullPointerException(空指针异常)
空指针异常在编程时也经常遇到,该异常的出现意味着“程序遇上了空指针”,简单地说就是调用了未经初始化的对象或者是不存在的对象,这个错误经常出现在调用数组的操作中。
3.1.1 代码实例(NullPointerException)
//空指针异常
int[] array = null;
System.out.println(array[2]);
输出结果:
![](https://img-blog.csdnimg.cn/img_convert/fefa2bf5447b509180272904d3f45320.png)
3.2 ClassCastException(类转换异常)
数据类型转换错误,比如:int temp= 123;如果设为String temp就会报错,因为它们类型不一样。
3.2.1 代码实例(ClassCastException)
//类转换异常
Object object = 88.8F;
int value = (int)object;
输出结果:
![](https://img-blog.csdnimg.cn/img_convert/da538d22b8b26cf0be0acb06eb141d32.png)
3.3 IndexOutOfBoundsException(数组下标越界异常)
我们在操作数组的时候经常会遇到这个异常,该异常的意思是“数组下标越界”,在使用数组的时候一定要认真,看自己调用的数组的下标是不是超出了数组的范围。
3.3.1 代码实例(IndexOutOfBoundsException)
//数组下标越界异常
int[] array = new int[5];
System.out.println(array[6]);
输出结果:
![](https://img-blog.csdnimg.cn/img_convert/b77d39545d8de81749ff59b8b9cfd37f.png)
3.4 IllegalAccessException(访问权限异常)
该异常的解释是“没有访问权限”,当应用程序要调用一个类,但当前的方法对该类没有访问权限便会出现该异常。
3.4.1 代码实例(IllegalAccessException)
package cn.exe.p2;
public class Test002 {
//访问权限异常
A a = new A();
int number = a.x;
}
class A{
private int x;
public int getX() {
return x;
}
public void setX(int x) {
this.x = x;
}
}
3.5 IOException(输入输出异常)
一般读写文件会出现这个异常,比如你想从C盘上读一个文件到你写的程序,如果C盘上没有这文件,就会出现该异常。
3.5.1 代码示例(IOException)
输出输入异常
File file = new File("hello.txt");
FileInputStream fis = new FileInputStream(file);
int data = fis.read();
输出结果:
![](https://img-blog.csdnimg.cn/img_convert/bb976b72426aa858613cc5d93517bf05.png)
3.6 其他的常见异常
算术异常:ArithmeticExecption
方法未找到异常:NoSuchMethodException
类转换异常:ClassCastException
字符串转换为数字异常:NumberFormatException
数组负下标异常:NegativeArrayException
数组下标越界异常:IndexOutOfBoundsException
文件已结束异常:EOFException
空指针异常:NullPointerException
违背安全原则异常:SecturityException
访问权限异常:IllegalAccessException
文件未找到异常:FileNotFoundException
操作数据库异常:SQLException
输入输出异常:IOException
……
Java异常处理:Java采用的异常处理机制,是将处理的程序代码集中在一起,与正常的程序代码分开,使程序简洁、优雅、并易于维护。
在处理异常时,主要使用两个方式:
方式一:try-catch-finally
方式二:throws + 异常类型
四、异常处理机制一【try-catch-finally】
4.1 try-catch-finally 的解释
①try:
捕获异常的第一个步骤是用try{....}语句选定捕获异常的范围,将可能出现异常的代码放在try语句中。
②catch:
在catch语句块中是对异常对象进行处理的代码,每个try语句块可以伴随一个或多个catch语句,用于处理可能产生的不同类型的异常对象。
捕获异常的有光信息,与其他对象一样,可以访问一个异常对象的成员变量或调用它的方法。其中:printStackTrace()获取异常类名和异常信息,以及异常出现在程序中的位置。getMessage()获取异常信息,返回字符串。
③finally:
捕获异常的最后一步是通过finally为异常处理提供一个统一的出口,使得在控制流程转到程序的其他部分以前,能够对程序的一个状态作统一的管理。
不管在try代码块中是否发生了异常事件,catch语句是否有异常,是否执行等情况,finally块中的语句都会被执行。
4.2 try-catch-finally的使用
try{
//可能出现异常的代码
}catch(异常类型1 变量名1){
//处理方式一
}catch(异常类型2 变量名2){
//处理方式二
}catch(异常类型3 变量名3){
//处理方式三
}
...
finally{
//一定会执行的代码
4.3 try-catch-finally 的说明
① finally是可选的
② 使用try将可能出现异常的代码包装起来,在执行过程中,一但出现异常,就会生成一个对应异常类的对象,根据此对象的类型,去catch中进行匹配。
③ 一旦try中的异常对象匹配到某一个catch时,就进入catch中进行异常的处理操作,一旦处理完成,就接着执行finally部分代码后再执行其后的代码,如果没有写finally部分,就直接执行后面的代码。
④ catch中的异常类型如果没有字父类关系,则二者谁声明上,都可以。
catch中的异常类型满足字父类关系,则要求子类一定要声明再父类的上面。
⑤ 常见的异常对象处理方式:(1)String getMessage() (2)printStackTrace()
⑥ try-catch-finally 结构可以嵌套
⑦ 使用try-catch-finally处理异常时,使得程序在编译时就不在报错,但是在运行时还有可能报错。(相当于我们使用try-catch-finally将一个编译时可能出现的报错延迟到运行时出现)
⑧ finally中声明的是一定会被执行的代码,即使catch中又出现了异常,try、catch中出现return语句等情况。
⑨ 在数据库连接、输入输出流、网路编程Socket等资源,JVM是不能自动回收的,我们需要自己动手进行资源的释放,这是资源的释放,就需要声明在finally中。
4.4 try-catch-finally代码示例
package cn.exe.p1;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
public class EXceptionTest {
public static void main(String[] args) {
EXceptionTest test = new EXceptionTest();
test.test1();
test.test2();
}
public void test1() {
try {
File file = new File("123.txt");
FileInputStream fis = new FileInputStream(file);
} catch (FileNotFoundException e) {
e.printStackTrace();
}catch(IOException e) {
e.printStackTrace();
}
}
public void test2() {
String str = "123";
str = "abc";
try {
int num = Integer.parseInt(str);
System.out.println("hello ---1");
}catch(NumberFormatException e) {
e.printStackTrace();
}catch(NullPointerException e) {
System.out.println("空指针异常");
}catch(Exception e) {
System.out.println("出现异常");
}finally{
System.out.println("hello -- 2");
}
}
}
五、异常处理机制二【throws】
5.1 throws的使用
“throws + 异常类型”写在方法的声明处,指明此方法执行时,可能会抛出的异常类型。
当方法体执行时,出现异常,仍会在异常代码处生成一个异常类的对象,此对象满足throws后的异常类型时,就会被抛出,异常代码后续的代码,就会不会再执行。
5.2 异常对象的产生
① 系统自动生成的异常对象
② 手动生成一个异常对象,并抛出
5.3 throws代码示例
package cn.exe.p1;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
public class ExceptionTest2 {
public static void main(String[] args) {
try {
method2();
}catch(IOException e) {
e.printStackTrace();
}
}
public static void medthod3() {
try {
method2();
}catch(IOException e) {
e.printStackTrace();
}
}
public static void method2() throws IOException{
method1();
}
public static void method1() throws FileNotFoundException,IOException{
File file = new File("123.txt");
FileInputStream fis = new FileInputStream(file);
int data = fis.read();
while(data != -1) {
System.out.println((char)data);
data = fis.read();
}
fis.close();
System.out.println("hahaha!");
}
}
5.4 throws与try-catch-finally的区别
try-catch-finally:真正的将异常解决掉了
throws:只是将异常抛给了方法的调用者,并没有真正的将异常解决掉
六、用户自定义异常类
一般情况下,用户自定义异常类都是RuntimeException的子类
① 自定义的异常类通常需要编写几个重载的构造器
② 自定义的异常需要提供seriaIversionUID
③ 自定义的异常通过throws抛出
6.1 自定义异常的过程
(1)继承于现有的异常结构如:RuntimeException、Exception
(2)提供全局常量:seriaIVersionUID
(3)提供重载的构造器6
6.2 自定义异常代码示例
package cn.exe.p2;
import java.util.Scanner;
public class Test002 {
public static void main(String[] args) {
Person person = new Person();
try {
person.age(280);
}catch(Exception e) {
e.printStackTrace();
}
}
}
class Person{
public static void age(int age) throws MyAgeException{
Scanner scanner = new Scanner(System.in);
while(true) {
if(age < 0 || age > 150) {
throw new MyAgeException("抱歉,输入的年龄有误");
}else {
System.out.println("输入的年龄无误");
break;
}
}
}
}
输出结果:
![](https://img-blog.csdnimg.cn/img_convert/78f1983871c7206b88b1814aa6c27073.png)
最后到这里,文章就结束了,如果在内容上有问题,恳请各位大佬指出。