Java自学者论坛

 找回密码
 立即注册

手机号码,快捷登录

恭喜Java自学者论坛(https://www.javazxz.com)已经为数万Java学习者服务超过8年了!积累会员资料超过10000G+
成为本站VIP会员,下载本站10000G+会员资源,会员资料板块,购买链接:点击进入购买VIP会员

JAVA高级面试进阶训练营视频教程

Java架构师系统进阶VIP课程

分布式高可用全栈开发微服务教程Go语言视频零基础入门到精通Java架构师3期(课件+源码)
Java开发全终端实战租房项目视频教程SpringBoot2.X入门到高级使用教程大数据培训第六期全套视频教程深度学习(CNN RNN GAN)算法原理Java亿级流量电商系统视频教程
互联网架构师视频教程年薪50万Spark2.0从入门到精通年薪50万!人工智能学习路线教程年薪50万大数据入门到精通学习路线年薪50万机器学习入门到精通教程
仿小米商城类app和小程序视频教程深度学习数据分析基础到实战最新黑马javaEE2.1就业课程从 0到JVM实战高手教程MySQL入门到精通教程
查看: 302|回复: 0

Java 异常的捕获与处理详解(二)

[复制链接]
  • TA的每日心情
    奋斗
    4 天前
  • 签到天数: 789 天

    [LV.10]以坛为家III

    2049

    主题

    2107

    帖子

    72万

    积分

    管理员

    Rank: 9Rank: 9Rank: 9

    积分
    722638
    发表于 2021-5-19 16:29:22 | 显示全部楼层 |阅读模式

    (一)、throws关键字

      throws关键字主要是在定义上使用的,表示的是此方法中不进行异常处理,而交给被调用处处理。

      例如:

    1 class MyMath {
    2     public int div(int x, int y) throws Exception {
    3         return x / y;
    4     }
    5 }

      现在div()方法之中抛出一个异常出来,表示所有异常交给被调用处进行处理。

     1 class MyMath {
     2     public int div(int x, int y) throws Exception {
     3         return x / y;
     4     }
     5 }
     6 
     7 public class Test {
     8     public static void main(String args[]) {
     9         try {
    10             System.out.println(new MyMath().div(10, 0));
    11         } catch (Exception e) {
    12             e.printStackTrace();
    13         }
    14     }
    15 }

    运行结果:

    1 java.lang.ArithmeticException: / by zero
    2     at MyMath.div(Test.java:3)
    3     at Test.main(Test.java:10)

    注意:在调用throws关键字声明方法的时候,一定要使用异常处理操作进行异常的处理,这属于强制性的处理。

    而主方法本身也属于方法,那么在主方法上也可以继续使用throws进行异常的抛出:

     

     1 class MyMath {
     2     public int div(int x, int y) throws Exception {
     3         return x / y;
     4     }
     5 }
     6 
     7 public class Test {
     8     public static void main(String args[]) throws Exception {
     9         System.out.println(new MyMath().div(10, 0));
    10     }
    11 }

     

    运行结果:

    1 Exception in thread "main" java.lang.ArithmeticException: / by zero
    2     at MyMath.div(Test.java:3)
    3     at Test.main(Test.java:9)

    这时主方法将异常继续向上抛,交给JVM进行异常的处理,也就是采用默认的方式,输出异常信息,而后结束程序执行。

    注意:在实际开发中,主方法不要加throws,因为程序如果有异常,我们也希望可以正常的结束。

    (二)throw关键字

      之前所有异常类的对象都是由JVM自动进行实例化操作的,用户自己也是可以手工地抛出一个异常类实例化对象,就通过throw完成了。

     

    1 public class Test {
    2     public static void main(String args[]) {
    3         try {
    4             throw new Exception("自定义的异常");
    5         } catch (Exception e) {
    6             e.printStackTrace();
    7         }
    8     }
    9 }

     

    运行结果:

    1 java.lang.Exception: 自定义的异常
    2     at Test.main(Test.java:4)

    小结:throw和throws的区别?

      (1)throw: 在方法体内使用,表示人为地抛出一个异常类对象(这个对象可以是自己实例化的,也可以是已经存在的)

     

     

     

      (2)throws: 在方法的声明上使用,表示此方法中不进行异常的处理,而交给被调用处处理。

     

    (三)、异常处理标准格式

    我们有种感觉,finally和throw没有用处。现要求定义一个div()方法,这个方法有如下的一些要求: 
    (1)在进行除法操作之前,输出一行提示信息; 
    (2)在除法操作执行完毕后,输出一行提示信息; 
    (3)如果中间产生了异常,则应该交给被调用处来进行处理。

     1 class MyMath {
     2     // 出现异常要交给被调用处出,使用throws
     3     public int div(int x, int y) throws Exception {
     4         System.out.println("===== 计算开始 ====="); 
     5         int result = 0;
     6         try {
     7             result = x / y; // 除法计算
     8         } catch (Exception e) {
     9             throw e; // 向上抛
    10         } finally {
    11             System.out.println("===== 计算结束 ====="); 
    12         }
    13         return result;
    14     }
    15 }
    16 
    17 public class Test {
    18     public static void main(String args[]) {
    19         try {
    20             System.out.println(new MyMath().div(10, 0));
    21         } catch (Exception e) {
    22             e.printStackTrace();
    23         }
    24     }
    25 }

    运行结果:

    1 ===== 计算开始 =====
    2 ===== 计算结束 =====
    3 java.lang.ArithmeticException: / by zero
    4     at MyMath.div(Test.java:7)
    5     at Test.main(Test.java:20)

    以上代码也可以做一些简化:

     1 class MyMath {
     2     // 出现异常要交给被调用处出,使用throws
     3     public int div(int x, int y) throws Exception {
     4         System.out.println("===== 计算开始 ====="); 
     5         int result = 0;
     6         try {
     7             result = x / y; // 除法计算
     8         } finally {
     9             System.out.println("===== 计算结束 =====");
    10         }
    11         return result;
    12     }
    13 }
    14 
    15 public class Test {
    16     public static void main(String args[]) {
    17         try {
    18             System.out.println(new MyMath().div(10, 0));
    19         } catch (Exception e) {
    20             e.printStackTrace();
    21         }
    22     }
    23 }

    运行结果:

    1 ===== 计算开始 =====
    2 ===== 计算结束 =====
    3 java.lang.ArithmeticException: / by zero
    4     at MyMath.div(Test.java:7)
    5     at Test.main(Test.java:18)

    直接使用try…finally,不带有catch,那么就连处理的机会都没有了,所以不建议使用try…finally。标准格式是try…catch、finally、throws、throw一起使用。

     

    (四)、RuntimeException类

      先来观察一段代码

    1 public class Test {
    2     public static void main(String args[]) {
    3         String str = "123";
    4         int num = Integer.parseInt(str);
    5         System.out.println(num * num);
    6     }
    7 }

    运行结果:

    1 15129

    这个程序就是将一个字符串变为了基本数据类型,而后执行乘法操作,但是下面来看一下parseInt()方法定义:

    1 public static int parseInt(String s) throws NumberFormatException

    发现这个方法上抛出了一个NumberFormatException的异常,按照之前所讲,如果存在了throws,则必须使用try…catch进行处理,可是现在却没有强制要求处理,这是为什么呢? 
    来观察一下NumberFormatException的继承结构:

    1 java.lang.Object
    2    |- java.lang.Throwable
    3       |- java.lang.Exception
    4           |- java.lang.RuntimeException
    5               |- java.lang.IllegalArgumentException
    6                   |- java.lang.NumberFormatException

    发现NumberFormatException属于RuntimeException的子类,而在Java之中明确规定:对于RuntimeException的异常类型,在编译的时候不会强制性的要求用户处理,用户可以根据需要有选择性的来进行处理,在开发之中,如果没有处理,那么出现异常之后将交给JVM默认进行处理。也就是说,RuntimeException的子异常类,可以由用户根据需要有选择性的来进行处理。

    小结:RuntimeException和Exception的区别?请列举出几个常见的RuntimeException.

    (1)RuntimeException是Exception的子类; 
    (2)Exception定义了必须处理的异常,而RuntimeException定义的异常可以选择性的进行处理。

    常见的RuntimeException: 
    NumberFormatException、ClassCastException、NullPointerException、ArithmeticException、ArrayIndexOutOfBoundsException。

     

    五、assert关键字(断言)

    Java中断言指的是程序执行到某行之后,其结果一定是预期的结果,而在JDK 1.4之后增加了一个assert关键字。

    两种语法形式: 
    (1)形式一:

    1 assert condition;

    这里condition是一个必须为真(true)的表达式。如果表达式的结果为true,那么断言为真,并且无任何行动 
    如果表达式为false,则断言失败,则会抛出一个AssertionError对象。这个AssertionError继承于Error对象。

    (2)形式二:

    1 asser condition:expr;

    这里condition是和上面一样的,这个冒号后跟的是一个表达式,通常用于断言失败后的提示信息,说白了,它是一个传到AssertionError构造函数的值,如果断言失败,该值被转化为它对应的字符串,并显示出来。

    使用断言:

    1 public class Test {
    2     public static void main(String args[]) {
    3         int x = 10;
    4         // 假设经过了若干操作
    5         assert x == 30 : "x的内容不是30";
    6         System.out.println(x);
    7     }
    8 }

    默认情况下,Java之中的断言,不会在正常执行的代码中出现,如果要想启用断言,则应该增加-ea选项:

    1 java -ea Test

    运行结果:

    1 Exception in thread "main" java.lang.AssertionError: x的内容不是30
    2         at Test.main(Test.java:5)

    (六)、自定义异常

    在Java之中本身已经提供了大量的异常类型,但是在开发之中,这些异常类型还不能满足于开发的需要。所以在一些系统架构之中往往会提供一些新的异常类型,来表示一些特殊的错误,而这种操作就称为自定义异常类,而要想实现这种自定义异常类,那么可以让一个类继承Exception或RuntimeException。

     1 class MyException extends Exception { // 自定义异常类
     2     public MyException(String msg) {
     3         super(msg);
     4     }
     5 }
     6 
     7 public class Test {
     8     public static void main(String args[]) throws Exception {
     9         throw new MyException("自己的异常类");
    10     }
    11 }

    运行结果:

    Exception in thread "main" MyException: 自己的异常类
        at Test.main(Test.java:9)

    参考链接: http://blog.csdn.net/wei_zhi/article/details/52837635

     

    哎...今天够累的,签到来了1...
    回复

    使用道具 举报

    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    QQ|手机版|小黑屋|Java自学者论坛 ( 声明:本站文章及资料整理自互联网,用于Java自学者交流学习使用,对资料版权不负任何法律责任,若有侵权请及时联系客服屏蔽删除 )

    GMT+8, 2024-9-10 03:43 , Processed in 1.035426 second(s), 29 queries .

    Powered by Discuz! X3.4

    Copyright © 2001-2021, Tencent Cloud.

    快速回复 返回顶部 返回列表