Java异常
异常 : 异常就是代表程序出现了问题
- 异常在代码中的作用
- 异常是用来查询bug的关键参考信息
- 异常可以作为方法内部的一种特殊返回值 以便通知调用者底层的执行情况
error
error代表系统级别的错误 (属于严重问题) 系统一旦出现问题,sun公司会把这些错误封装成error对象
error是给sun公司自己用的 不是给我们程序员用的 因此我们开发人员不用管他
Exception
exception : 叫做异常 代表程序可能出现的问题
我们通常会用exception以及他的子类来封装程序出现的问题
exception又分为运行时异常(RuntimeException) 于 其他异常(编译时异常)
编译时异常
编译阶段就出现异常提醒的 (如 语法错误 日期解析异常)
除了 runtimeexception 和它的子类 其他都是编译时异常 编译阶段就需要进行处理
RuntimeException
RuntimeException及其子类 编译阶段不会出现异常提醒 运行时出现的异常 (如空指针异常 数组越界异常)
JVM虚拟机默认处理异常
- 把异常的名称 异常原因以及异常出现位置等信息输出在控制台
- 程序停止运行 下面的代码不会运行
// 下标越界异常
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: Index 11 out of bounds for length 10
at test.test.main(test.java:21)
try…catch 捕获异常
如果捕获到了出现的异常 程序会正常往下执行
// 格式
/*
try{
可能出现异常的代码
}catch(异常类名 变量名){
// 捕获到异常执行 catch 中的代码
......
}catch(...){
...
}
*/
public static void main(String[] args) {
int[] arr=new int[10];
try{
System.out.println(arr[11]); // 此处出现了异常 程序就会在这创建一个 ArrayIndexOutOfBoundsException 对象
// 拿着这个对象到catch中的小括号进行对比 看小括号中的类型是不是当前类型及其父类
// 如果能被接收 就表示该异常就被捕获 执行匹配的 catch 里的代码
// 当 catch 里的所有代码执行完毕 程序则继续执行 try...catch 后面的代码`
}catch (ArrayIndexOutOfBoundsException e){
System.out.println("数组越界");
}
System.out.println("end");
}
// 输出结果
数组越界
endl
如果try中没有遇到异常 怎么执行
# 如果try中没有遇到异常 会执行完try中的所有的代码后继续往下执行 不会执行catch中的代码
如果try中遇到多个异常 怎么执行
# 写多个catch与之对应 如果我们要捕获多个异常 这些异常如果存在继承关系 父类一定要写在子类下面
# 程序遇到第一个异常 找到与之对应的catch 执行完成之后 跳出try...catch 不会执行try中剩下的代码
如果try中遇到的异常没有被捕获 怎么执行
# 如果遇到的异常没有被捕获 异常就会被JVM虚拟机进行处理
如果try中遇到了异常 那么try中下面的其他代码还会执行吗
# 不会被执行 如果try中遇到了异常 则会匹配下面的 catch, 如果匹配不到 则会交给JVM虚拟机进行执行
异常中的常见方法
方法名称 | 说明 |
---|---|
public String getMessage() | 返回此thriowable 的详细消息字符串 |
public String toString() | 返回此可抛出的简短描述 |
public void printStackTrace() | 把异常的错误信息输出在控制台 |
public static void main(String[] args) {
int[] arr = new int[10];
try {
System.out.println(arr[11]);
} catch (ArrayIndexOutOfBoundsException e) {
System.out.println(e.toString());
// 输出结果
// java.lang.ArrayIndexOutOfBoundsException: Index 11 out of bounds for length 10
System.out.println(e.getMessage());
// 输出结果
// Index 11 out of bounds for length 10
e.printStackTrace();
// 在底层是使用 System.err.println 进行输出
// 把异常的错误信息以红色字体输出在控制台
// 仅仅是打印信息 不会停止程序
// 输出结果
/*
java.lang.ArrayIndexOutOfBoundsException: Index 11 out of bounds for length 10
at test.test.main(test.java:23)
*/
}
}
抛出异常
throws
写在方法定义处 表示声明一个异常 如果异常有多个 以,
隔开
public void 方法名() throws 异常1,异常2,异常...{
...
}
// 编译时异常 : 必须要写
// 运行时异常 : 可以不写
throw
写在方法内 结束方法 手动抛出异常对象 交给调用者 方法中剩下的代码不再执行
public void 方法名() throws ArrayIndexOutOfBoundsException{
// 抛出一个数组越界异常
throw new ArrayIndexOutOfBoundsException();
}
自定义异常
自定义异常的意义 : 就是为了让控制台的报错信息更加的见名知意
- 定义异常类
- 继承异常
- 空参 与 带参构造
// 自定义一个年龄范围异常
public class AgeScopeException extends RuntimeException{
public AgeScopeException() {
}
public AgeScopeException(String message) {
// 异常的带参构造会把字符串输出在控制台
super(message);
}
}
public class Stu {
int age;
public Stu(int age) {
setAge(age);
}
public Stu() {
}
public int getAge() {
return age;
}
public void setAge(int age) {
if(age>=0&&age<=100){
this.age = age;
}else{
// 抛出异常
throw new AgeScopeException(age+"不在范围内");
}
}
}
测试异常
public class test {
public static void main(String[] args) {
new Stu(101);
}
}
// 控制台输出结果为
/*
Exception in thread "main" test.AgeScopeException: 101不在范围内
at test.Stu.setAge(Stu.java:21)
at test.Stu.<init>(Stu.java:7)
at test.test.main(test.java:20)
*/