Java中的异常与处理

Java中的异常

在程序运行时发生了不正常的情况,此时由系统中断程序的运行,包含异常信息、异常类名、异常的位置。

异常分类
  • Error 错误
    由系统原因造成的,一般是系统资源分配冲突时或系统崩溃等原因,这一类Error错误,对于程序员来说是无法处理的
  • Exception
    由于程序原因造成的,一般是运算、I/O读取等原因,这一类Exception异常,可以进行处理
Java中异常类的体系

Throwable、Error、Exception

在Java中如何处理异常?

1、捕获异常处理

      try{
       可能出现异常的语句;
      }catch(异常类型 对象名){
       处理异常语句;
       }

2、抛出异常

  • 声明方法时抛出异常

    方法名() throws 异常类名[,异常类名,异常类名] {}
    
  • 在方法中抛出异常

    RuntimeException :非受控异常(运行时异常)  
    

案例

public class Demo {

    static int divide(int a, int b) throws ArithmeticException {
        int result = 0;

        result = a / b; //当发生异常时,向调用者抛出异常

        //当异常从某一位置抛出后,其下的语句不会被执行
        System.out.println("计算结果完成....");

        return result;
    }


    public static void main(String[] args) {
        //输入两个数
        Scanner scanner = new Scanner(System.in);

        //将数字字符串转成数值类型
        int a = scanner.nextInt();
        int b = scanner.nextInt();
        scanner.close();
        try {
            int r = divide(a, b);

            System.out.println(r);

        } catch (Exception e) { //可以处理所有异常,即Exception类是所有异常的父类
            e.printStackTrace();
        }


    }
}

运行结果

Java中的异常与处理_第1张图片

多个异常处理方式

    try{

    }catch(异常类名 对象名){

    }catch(...){

    }catch(...){

    }

注意:处理多个异常类时,异常的子类所在的catch语句要放在最上面。

案例

public class Demo {
    static class Person {
        String name;

        public Person(String name) {
            this.name = name;
        }

        public String toString() {
            return "[name=" + name + "]";
        }
    }

    static void sub(int a, int b, int[] nums, Person p) {
        try {
            int r = a / b;//此行如果出现了异常,则下行代码不会执行
            r = nums[5] / 9;
            System.out.println(p);
        } catch (ArithmeticException e) {
            System.out.println("除数为0了...");
        } catch (ArrayIndexOutOfBoundsException e) {
            System.out.println("数组的索引值越界了,数组的长度小于6...");
        } catch (NullPointerException e) {
            System.out.println("访问的对象是null");
        } catch (Exception e) {  //异常类的父类所处于的catch语句要放在最后
            e.printStackTrace();
        }

    }

    public static void main(String[] args) {
        int[] nums = {9, 10, 8, 66, 22, 109};

        sub(10, 2, nums, new Person("张三"));

        sub(10, 0, new int[3], null);

    }
}

抛出异常

  • 抛出多个异常

    在方法声明的后边,使用 throws 异常类型列表 语句。

  • 抛出一个异常
    throw new RuntimeException("异常信息")

案例

public class Demo {

    static class Person {
        String name;

        public Person(String name) {
            this.name = name;
        }

        public String toString() {
            return "[name=" + name + "]";
        }
    }

    //抛出多个异常,抛给调用者处理
    static void sub(int a, int b, int[] nums, Person p)
            throws ArithmeticException, IndexOutOfBoundsException, NullPointerException {

        int r = a / b;//此行如果出现了异常,则下行代码不会执行
        r = nums[5] / 9;
        //System.out.println(p.toString());

    }

    static void div(int a, int b) {
        if (b == 0) {
            //抛出异常
            throw new RuntimeException("除数为0");
        }
    }

    public static void main(String[] args) {
        int[] nums = {9, 10, 8, 66, 22, 109};

        //sub(10,2,nums,new Person("张三"));

        try {
            sub(10, 4, new int[7], null);

            div(9, 0);

        } catch (ArrayIndexOutOfBoundsException e) {
            System.out.println("数组长度小于6");
        } catch (IndexOutOfBoundsException e) {  //父类的异常处理放在子类异常处理的下方
            System.out.println("索引越界。。。");
        } catch (Exception e) {
            e.printStackTrace();
        }

    }

}

处理异常的格式(正规的)

try{
 //资源分配的语句
 }catch(...){

}finally{
//肯定执行的语句,一般是释放资源的语句,
 //注: 如果try语句中包含return 语句,finally语句在return之前执行
 }

案例

public class Demo {

    static class Student{
        private String name;
        public Student(String name){
            this.name=name;
        }

        public int div(int a,int b){
            return a/b;
        }

        public String toString(){
            return name;
        }
    }

    public static void main(String[] args){
        Student s=new Student("张三");

        try{
            s.div(10,0);

            return ;
        }catch(Exception e){
            e.printStackTrace();
        }finally{
            System.out.println(s.toString());

            s=null;//s所指向的堆内存变是垃圾了,可以被gc回收

            System.out.println("回收资源...");
        }
    }
}

自定义异常

自定义异常类步骤

1、创建类,并继承Exception

2、提供构造方法,可以调用父类的构造方法

3、使用自定义的类时在方法中,根据条件判断的结果,再通过throw关键向方法的调用者抛出异常

如:

  void method(int a){
   if(a<0){
  throw new 自定义异常类型("异常信息");
  }

注意:对于抛出的自定义的Exception异常,必须要处理

案例

public class Demo {
    static class MyException extends Exception {
        public MyException() {
            super("自定义异常");
        }

        public MyException(String msg) {
            super(msg);
        }
    }

    static void isZero(int n) throws MyException {
        if (n < 0) {
            //抛出数值不能小于0的异常
            throw new MyException("数值不能小于0!!"); //抛出的一般性异常必须要处理:捕获或抛出
        }

        System.out.println("大于0的值--》" + n);
    }

    public static void main(String[] args) {

        try {
            isZero(-1);
        } catch (MyException e) {
            e.printStackTrace();
        }

    }
}

补充

Error和Exception有什么区别?

Error表示系统级的错误和程序不必处理的异常,是恢复不是不可能但很困难的情况下的一种严重问题;比如内存溢出,不可能指望程序能处理这样的情况;Exception表示需要捕捉或者需要程序进行处理的异常,是一种设计或实现问题;也就是说,它表示如果程序运行正常,从不会发生的情况。

try{}里有一个return语句,那么紧跟在这个try后的finally{}里的代码会不会被执行,什么时候被执行,在return前还是后?

会执行,在方法返回调用者前执行。

阐述final、finally、finalize的区别
  • final:修饰符(关键字)有三种用法:如果一个类被声明为final,意味着它不能再派生出新的子类,即不能被继承,因此它和abstract是反义词。将变量声明为final,可以保证它们在使用中不被改变,被声明为final的变量必须在声明时给定初值,而在以后的引用中只能读取不可修改。被声明为final的方法也同样只能使用,不能在子类中被重写。
  • finally:通常放在try…catch…的后面构造总是执行代码块,这就意味着程序无论正常执行还是发生异常,这里的代码只要JVM不关闭都能执行,可以将释放外部资源的代码写在finally块中。
  • finalize:Object类中定义的方法,Java中允许使用finalize()方法在垃圾收集器将对象从内存中清除出去之前做必要的清理工作。这个方法是由垃圾收集器在销毁对象时调用的,通过重写finalize()方法可以整理系统资源或者执行其他清理工作。
说出下面运行结果:类ExampleA继承Exception,类ExampleB继承ExampleA。
  try {
    throw new ExampleB("b")
  } catch(ExampleA e){
    System.out.println("ExampleA");
  } catch(Exception e){
    System.out.println("Exception");
  }

输出:ExampleA。

常见的运行时异常?
  • NullPointerException (空指针异常)
  • IndexOutOfBoundsException (下标越界异常)
  • ClassCastException (类转换异常)
  • IllegalArgumentException (非法参数异常)
  • ArithmeticException(算术异常)

你可能感兴趣的:(Java中的异常与处理)