zoukankan      html  css  js  c++  java
  • 异常

    异常:

                   在程序运行过程中,出现的不正常情况叫做异常。

    在解决代码中可能出现的异常,要添加非常多的逻辑来进行判断,会使代码变得非常臃肿,不利于维护,因此,推荐大家使用异常处理机制来处理程序运行过程中出现的问题。

    捕获异常:try、catch、finally

    声明异常:throws

    抛出异常:throw

    获取错误信息:e.printStackTrace();(常用)    e.getmessage();(不常用)

    finally块:

                     在程序运行过程中,如果处理异常的部分包含finally的处理,那么无论代码是否发生异常,finally中的代码总会执行。

                      finally中包含哪些处理逻辑?

                               1、IO流的关闭操作一般设置在finally中;

                               2、数据库的连接关闭操作一般设置在finally中;

    面试中常问的问题:

                      try..catch块中存在return语句,是否还执行finally块,如果执行,说出执行顺序?

    情况一:try中有return,finally中没有

     1 package com.test.ExceptionQuestion;
     2 
     3 public class Demo {
     4     public static void main(String[] args) {
     5         System.out.println(test());
     6     }
     7 
     8     public static int test(){
     9         int num = 10;
    10         try{
    11             System.out.println("try");
    12             return num += 80;//等待finally执行结束后在执行
    13         }catch (Exception e){
    14             System.out.println("error");
    15         }finally {
    16             if(num>20){
    17                 System.out.println("num>20 :"+num);
    18             }
    19             System.out.println("finally");
    20         }
    21         return num;
    22     }
    23 }
    tryCatchReturn

    情况二:try和finally中均有return

     1 package com.test.ExceptionQuestion;
     2 
     3 public class Demo {
     4     public static void main(String[] args) {
     5         System.out.println(test());
     6     }
     7 
     8     public static int test(){
     9         int num = 10;
    10         try{
    11             System.out.println("try");
    12             return num += 80;//等待finally执行结束后执行
    13         }catch (Exception e){
    14             System.out.println("error");
    15         }finally {
    16             if(num>20){
    17                 System.out.println("num>20 :"+num);
    18             }
    19             System.out.println("finally");
    20             num =100;
    21             return num;
    22         }
    23     }
    24 }
    tryCatchReturn02

    情况三:finally中改变返回值num

     1 package com.test.ExceptionQuestion;
     2 
     3 public class Demo {
     4     public static void main(String[] args) {
     5         System.out.println(test());
     6     }
     7 
     8     public static int test(){
     9         int num = 10;
    10         try{
    11             System.out.println("try");
    12             return num;
    13         }catch (Exception e){
    14             System.out.println("error");
    15         }finally {
    16             if(num>20){
    17                 System.out.println("num>20 :"+num);
    18             }
    19             System.out.println("finally");
    20             num =100;
    21         }
    22         return num;
    23     }
    24 }
    tryCatchReturn03

    情况四:将num的值包装在Num类中

     1 package com.test.ExceptionQuestion;
     2 
     3 public class Demo {
     4     public static void main(String[] args) {
     5         System.out.println(test().num);
     6     }
     7 
     8     public static Num test(){
     9         Num number = new Num();
    10         try{
    11             System.out.println("try");
    12             return number;
    13         }catch (Exception e){
    14             System.out.println("error");
    15         }finally {
    16             if(number.num>20){
    17                 System.out.println("number.num>20 :"+number.num);
    18             }
    19             System.out.println("finally");
    20             number.num =100;
    21         }
    22         return number;
    23     }
    24 }
    25 class Num{
    26     public int num = 10;
    27 }
    tryCatchReturn04

    执行结果:

    情况一:

    try
    num>20 :90
    finally

    90

    分析:显然try的return num+=80被分成两句话1、num =num+80;2、return num;  先执行1,并把num=80保存起来,在try中的return num执行之前,先执行finally块,finally执行结束,然后在将90返回。

    情况二:

    try
    num>20 :90
    finally
    100

    分析:try中的return扔被分成了两句,finally中的return语句先于try中return语句的执行,所以try中的return被覆盖了,所以不再执行。

    情况三:

    try

    finally

    10

    分析:虽然在finally中改变了num的值,但因为finally中并没有返回该num的值,因此在执行完finally中的语句后,test()会得到try中返回的num值,而try中的num值依然是程序进入finally前保留下来的值,因此直接返回了

    情况四:

    try
    finally
    100

    从结果中可以看出,同样是在finally中改变了返回值num的值,在情况三中并没有被try中的return返回,但在这里却被try中的return语句返回了。

    结论:

                     try语句再返回前,将其他所有的操作执行完,保留好要返回的值,而后转入执行finally的语句,然后分为以下三种情况:

                     1、如果finally中有return语句,则覆盖掉try中的return语句,直接执行finally中的return语句,得到返回值,这样便无法得到try中之前保留好的返回值;

                     2、如果finally中没有return语句,也没有改变要返回值,则执行完finally语句后,会接着执行try中的return语句,返回之前保留好的值;

                     3、如果finally中没有return语句,但是改变了要返回值,这里有点类似于引用传递和值传递的区别,分一下两种情况:

                                1)、如果return的数据类型是基本数据类型或者文本字符串,则在finally中对基本数据的改变不起作用,try中的return依然会返回进入finally之前保留的值;

                                2)、如果return的数据是引用数据类型,则在finally中对该引用数据类型的属性的改变是起作用的,try中的return返回的就是finally中改变后的该属性值。

            在异常情况出现的时候,可以使用try...catch...finally的方式对异常进行处理,除此之外,可以将异常向外抛出,由外部进行处理。

    throws:声明异常

                    在方法的调用中,可能存在多个方法之间的调用,此时如果每个方法都包含了异常情况,则需要在每个方法中都进行try...catch。另外一种比较简单的方式,就是在方法的最外层调用一次即可,使用throws方法,对所有执行过程中所有的方法出现的异常进行统一集中的处理。

                     如何判断使用try..catch还是throws?

                     最稳妥的方法是都进行异常捕获

                     偷懒的方式是判断整个调用过程中,外层的方法是否对异常进行了处理,如果处理了则直接使用throws,如果没有,则使用try...catch。

    throw:抛出异常

    自定义异常:

                     在java的api中提供了非常丰富的异常类,但是在某些情况下不太满足我们的需求,此时需要自定义异常

                     步骤:

                              1、继承Exception类;

                              2、需要自己定义其构造方法;

                              3、需要使用时,使用throw new  自定义异常名称;

                      什么时候使用自定义异常?

                               一般情况下不需要

                              但是在公司明确规定,或者要求异常格式规范统一的时候是必须要自定义异常。

     1 package com.test.ExceptionQuestion;
     2 
     3 public class GenderException extends Exception {
     4     public GenderException() {
     5         System.out.println("性别异常");
     6     }
     7 
     8     public GenderException(String msg) {
     9         System.out.println(msg);
    10     }
    11 }
    GenderException
     1 package com.test.ExceptionQuestion;
     2 
     3 public class Demo {
     4     public static void main(String[] args) {
     5         try{
     6             test();
     7         }catch (GenderException e){
     8             e.printStackTrace();
     9         }finally{
    10             System.out.println("欢迎光临");
    11         }
    12     }
    13 
    14     public static void test() throws GenderException{
    15 
    16         String gender = "111";
    17         if("woman".equals(gender)){
    18             System.out.println("女人");
    19         }if("man".equals(gender)){
    20             System.out.println("男人");
    21         }else{
    22             throw new GenderException("什么玩应儿。。。。");
    23         }
    24     }
    25 }
    Test

     异常的分类:

                       异常是以Throwable为顶层父类,在派生出Error类和Exception类。

                        Error类:这一类的错误是JVM本身的错误,一般很少出现,一旦出现就是很严重的,程序员也是处理或解决不了的;

                        Exception类:(由java应用程序抛出和处理的非常严重的错误)

                                  分为检查/编译时异常(checkedException,程序必须处理该异常)和运行时异常(不要求程序员必须做出处理,但最好避免);

                        在Java的标准包java.lang java.util 和 java.net 中定义的异常都是非运行异常

    常见的异常类型:

                         

                    

     
  • 相关阅读:
    密码学复习
    Kafka Stream 高级应用
    Kafka Stream 流和状态
    Kafka Stream 处理器API
    SSM工作流程与原理详解
    Seata AT和XA模式
    分布式锁结合SpringCache
    使用RabbitMQ最终一致性库存解锁
    使用Springboot+SpringCloud+Seata1.3.0+Nacos1.2.1进行全局事务管理
    在微服务环境下,远程调用feign和异步线程存在请求数据丢失问题
  • 原文地址:https://www.cnblogs.com/bentuzi/p/12636981.html
Copyright © 2011-2022 走看看