异常
异常 分为error和exception 。
- error是包括jvm在内的,对于内存分配不够, jvm内部错误等 非程序错误的异常
- exception是程序在运行过程中,因为程序存在逻辑错误等在内的和程序有关的异常,可通过修改程序解决
异常的结构
异常的常见类型
int a[]={1,2,3,4,5};
System.out.println(a[5]); //数组越界异常 ArrayIndexOutOfBoundException
int b=10;
System.out.println(b/0); //数组越界异常 ArithmeticException
String str="abc";
int c=Integer.parseInt(str);
System.out.println(c); //数字格式转换异常 NumberFormatException
String str1=null;
System.out.println(str1.length()); //空指针异常 NullPointException
String str2="abcd";
Object obj=str2;
Integer i=(Integer) obj; //类型转换异常 ClassCastException
try-catch语句
try-catch语句用来处理可能会出现的异常,如果try里面的语句出现问题,就会直接去执行catch里面的语句,不会去执行try里面后面的语句
try{ int c[]={1,2,3,4,5}; //防止程序出错,不影响程序后续的执行 System.out.println(c[5]);
}
catch (ArrayIndexOutOfBoundsException e){ //catch() 里面写出错的类型 System.out.println("数组越界");
}
try{
try { //异常里面嵌入异常
int d[]={1,2,3,4,5};
System.out.println(d[5]);
}catch (ArrayIndexOutOfBoundsException e){
System.out.println("数组越界");
}
int b=10;
System.out.println(b/0); //数组越界异常 ArithmeticException
}catch (ArithmeticException e){
System.out.println("除数不能为零");
}
try-catch-finally语句
finally语句用于当try-catch无论出错不出错,都回去执行finally语句
public class Demo2 {
public static void main(String[] args) {
int a = 10;
int b= 0;
try{
System.out.println(a/b);
}catch (ArithmeticException e){
System.out.println("除数不能为零"); //除数不能为零
}finally { //finally()语句 无论执行try还是catch语句 都会最终执行finally
System.out.println("最终会执行finally"); //最终会执行finally
}
System.out.println(chu(a,2));
}
static int chu(int a,int b){
try{
System.out.println(a/b);
return 0;
}catch (ArithmeticException e){
System.out.println("除数不能为零");
return -1;
}finally {
System.out.println("最终会执行finally"); //如果finally里面有返回值,则会覆盖掉try或者catch里面的返回值
return 1;
}
}
}
//输出
除数不能为零
最终会执行finally
5
最终会执行finally
1
如果有return值, finally里面的ruturn值会覆盖掉 try和catch里面的返回值
throw和throws
给一个方法throws声明一个异常,当程序出错的时候,会抛出这个异常
- throws用于抛异常的声明 throw主动去抛出异常
- throws抛出的异常 如果是编译期异常需要在调用方法的时候进行处理 如果是运行期异常则不需要处理
public static void main(String[] args) {
test(5);
System.out.println();
//test1();
try {
test2("abc"); //编译期异常 需要去处理
} catch (ParseException e) {
e.printStackTrace();
}
}
public static int test(int i){
if (i<100){
throw new ArithmeticException("数据不正常");
}
return 0;
}
public static void test1 () throws ArithmeticException{
System.out.println(10/0); //抛出异常 运行期异常 不需要处理
}
public static void test2(String str) throws ParseException{
int i=Integer.parseInt(str);
System.out.println(i);
}
当一个抽象类的抽象方法中声明抛出异常,则在继承之后,子类重写方法也需要去重新声明异常
public abstract class Demo4 {
//抽象类 里面的抽象方法 如果抛出异常 则子类在重写时也必须抛出异常
public abstract void eat() throws Exception;
public abstract void sleep() throws Exception;
}
public class Demo4Chrild extends Demo4{ //继承Demo4
@Override
public void eat() throws Exception { //抛出异常
}
@Override
public void sleep() throws Exception {
}
}
自定义异常,用于满足需求
public class scoreException extends Exception{
public scoreException() {
}
public scoreException(String message) {
super(message);
}
}
public class Demo5 {
//使用自定义的异常类处理
public static void main(String[] args) {
try {
test(101);
} catch (scoreException e) {
System.out.println(e.getMessage());
}
}
public static void test(int i) throws scoreException{
if (i>100 || i<0){
throw new scoreException("成绩有错");
}
}
}
//输出
成绩有误