java异常学习小结

java中,将程序运行中的发生的不正常情况称为异常。可将其分为错误和异常,错误是指java虚拟机无法解决的问题,常见有栈溢出(StackOver)和内存耗尽(OutOfMemory),异常又可以划分为两类,编译时异常(受检异常)和运行时异常(非受检异常)。如下图(简约版异常体系图)

 运行时异常是指RuntimeException及其子类,一般是由于代码设计的逻辑错误导致,不强制要求处理,但因为发生异常会默认采用将异常抛出的方式而导致程序崩溃,所以建议避免出现此类异常。

常见的运行时异常有

//        常见的运行时异常
//        NullPointerException
//                String str = null;
//                str.equals("");
//        Exception in thread "main" java.lang.NullPointerException

//        ArithmeticException 算术异常
//        eg
//        int nm = 1 / 0;
//        Exception in thread "main" java.lang.ArithmeticException: / by zero

//        ClassCastException 类型转换异常
//        eg.
//        Object obj = new String();
//        Integer ite = (Integer)obj;
//        Exception in thread "main" java.lang.ClassCastException: java.lang.String cannot be cast to java.lang.Integer

//        ArrayIndexOutOfBoundsException 索引越界异常
//        Integer [] arr = new Integer[3];
//        int i  = arr[3];
//        Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: 3

//        NumberFormatException 数字格式异常
//        eg
//        Integer.parseInt("123你");
//        Exception in thread "main" java.lang.NumberFormatException: For input string: "123你"

编译时异常故名思意,发生在编译阶段,如果不处理则无法通过编译

常见的编译时异常

SqlException

IoException

ClassNotFoundException

异常处理

1.throws 将异常抛出,交给方法的调用者解决(甩锅型)
2.try...catch...finally

throws的处理流程(一般用于不确定如何处理异常,将异常抛出,由调用者去处理)

eg.

    public static void main(String[] args) throws FileNotFoundException {
        InputStream is = new FileInputStream(new File("E:"));
}

 try...catch...finally使用

try{
    ...// 可能出现异常的代码
}
catch(xxxException e){
    ...//异常处理的逻辑
// 这里可以使用多个catch捕获不同的异常,如果多个catch捕获的异常中存在继承关系,必须先捕获子类异 
// 常
}
finally{
    ...// 一定会执行,多用于资源释放
    }
// 另外,三者可以进行多种组合,如try...finally/ try... catch 

关于 try...catch...finally的练习

    public static void main(String[] args) {
        try{
            System.out.println("异常发生前");
            int a = 1/0;
            System.out.println("异常发生后");
        }
        catch(ArithmeticException e){
            System.out.println("异常处理");
        }
        finally {
            System.out.println("关闭资源");
        }
    }

运行结果为

 不难看出,异常发生后,直接执行catch块中的语句,跳过try块中剩余的语句,最后执行finall块中的语句,这就是一个try...catch...finally的执行流程

  public static int testException(){
        int i;
        try {
            i = 1;
            i = i / 0;
            return i;
        }
        catch (ArithmeticException e){
            return i=3;
        }
        finally {
            return i = 4;
        }
    }

执行结果为

上述代码在发生异常进入catch块,执行 return语句 i = 3; 会将结果先寄存在栈中,并不会直接返回,然后执行finally语句,因为finally中也有return语句,就更新寄存的值并返回。

将上面的代码稍微改动一下

   public static int testException(){
        int i;
        try {
            i = 1;
            i = i / 0;
            return i;
        }
        catch (ArithmeticException e){
            return i=3;
        }
        finally {
           i = 4;
        }
    }

 执行结果

同样,发生异常进入catch块中执行return语句,这里将 3寄存在栈中,然后执行finally将 i的值改为3,但返回的值是栈中寄存的值。

再次改变上面的代码。每天上一当,当当不一样

 public static int[] testException(){
        try {
            arr[0] = 1;
            arr[0] = arr[0] / 0;
            return arr;
        }
        catch (ArithmeticException e){
            arr[0] = 3;
            return arr;
        }
        finally {
            arr[0]= 4;
        }
    }

 运行结果

arr[0] = 4;

和之前一样,发生异常执行catch中语句后执行return,将arr的地址寄存在栈中,finally执行后,返回之前catch块寄存在栈中的地址,在这之前对该地址指向空间的元素进行的修改都是有效的。

自定义异常类

作用:程序中出现的异常在Throwable的子类中没有描述处理,就可以通过diy的方式去设计异常类

方法:继承Exception或RuntimeException

        提供构造方法

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值