java中异常与return

抽时间整理了下java中异常与return,以前这块总是弄混淆,觉得还是写下来慢慢整理比较好。由于水平有限,仅供参考。废话不多说,直接上代码。

下面是两个方法:

 1      public static int throwReturn(){
 2         int ret = 0;
 3         try{
 4             ret = 10/0 ;
 5             ret++;
 6             return ret;
 7         }catch(Exception e){
 8             System.out.println("catch block " + e.getMessage());
 9             //ret++;
10             return ret;
11         }finally{
12             System.out.println("finally block invoked!!!");
13             ret++;
14             System.out.println("finally block invoked, ret is " + ret);
15         }
16         
17     }  
 1    public static int finallyReturn(){
 2         int ret = 0;
 3         try{
 4             ret = 10/0 ;
 5             ret++;
 6             return ret;
 7         }catch(Exception e){
 8             System.out.println("catch block " + e.getMessage());
 9             //ret++;
10             return ret;
11         }finally{
12             System.out.println("finally block invoked!!!");
13             ret++;
14             System.out.println("finally block invoked, ret is " + ret);
15             return ret;
16         }
17         
18     }

然后在主方法中分别调用两个方法:

1 public static void main(String args[]){
2   System.out.println("throwReturn:" + throwReturn());
3   //System.out.println("finallyReturn:" + finallyReturn());  
4 }

第一个方法输出结果:

catch block / by zero
finally block invoked!!!
finally block invoked, ret is 1
throwReturn:0

throwRetrun方法返回的结果并不是我预想的1,而是0。

个人分析:

  1. 程序执行到throwReturn方法的第4行时由于除0而出错,程序进入catch块,首先会执行打印输出:catch block / by zero
  2. 接下来会执行catch块的return ret语句,碰到return语句方法会返回退出,而finally语句又是必须执行的,此时程序会将return的结果值暂存起来,继续执行finally块。
  3. 进入finally块后会输出:finally block invoked!!! 和finally block invoked, ret is 1
  4. finally块执行完成后程序会回到return处,并返回当时暂存的值

第二个方法的输出结果:

catch block / by zero
finally block invoked!!!
finally block invoked, ret is 1
finallyReturn:1

哎,这次的输出结果是1了。

仔细比较两个方法发现第二个方法,在finally语句中多了一个return ret;程序的执行过程同上面基本上是一样的,只是在最终执行finally代码块是碰到了return语句,此时程序就直接将ret的值返回了,而此时ret的值是1,最后输出:finallyReturn:1

接下来我们再看2个方法:

 

 1     public static int throwException() throws Exception{
 2         int ret = 0;
 3         try{
 4             ret = 10/0 ;
 5             System.out.println("ret:" + ret);
 6             return ret;
 7         }catch(Exception e){
 8             System.out.println("catch block " + e.getMessage());
 9             throw e;
10         }finally{
11             System.out.println("finally block invoked!!!");
12             ret++;
13             System.out.println("finally block invoked, ret is " + ret);
14         }
15         
16     }

 

 1 public static int finallyThrowException() throws Exception{
 2         int ret = 0;
 3         try{
 4             ret = 10/0 ;
 5             System.out.println("ret:" + ret);
 6             return ret;
 7         }catch(Exception e){
 8             System.out.println("catch block " + e.getMessage());
 9             throw e;
10         }finally{
11             System.out.println("finally block invoked!!!");
12             ret++;
13             System.out.println("finally block invoked, ret is " + ret);
14             return ret;
15         }
16         
17     }

然后在主方法中分别调用两个上面方法:

 

 1 public static void main(String args[]){
 2        try {
 3             System.out.println("throwException:" + throwException());
 4         } catch (Exception e) {
 5             System.out.println("捕获到throwException方法抛出的异常," + e.getMessage());
 6         } 
 7 
 8         /*try {
 9             System.out.println("finallyThrowException:" + finallyThrowException());
10         } catch (Exception e) {
11             System.out.println("捕获到finallyThrowException方法抛出的异常," + e.getMessage());
12         }*/     
13 }

 

第一个方法输出结果:

catch block / by zero
finally block invoked!!!
finally block invoked, ret is 1
捕获到throwException方法抛出的异常,/ by zero

个人分析:

  1. throwException方法执行到第4行时,因为除0操作抛出异常,程序进入catch块,首先执行打印输出:catch block / by zero
  2. 接下来会执行catch块的throw e语句,向上抛出异常,而finally语句又是必须执行的,此时程序会先执行finally块。
  3. 进入finally块后会输出:finally block invoked!!! 和finally block invoked, ret is 1
  4. finally块执行完成后程序会回到catch块throw处,将捕获的异常向上抛出
  5. 在main方法中会捕获到throwException方法抛出的异常而进入catch块,所以会输出:捕获到throwException方法抛出的异常,/ by zero

第二个方法的输出结果:

 

catch block / by zero
finally block invoked!!!
finally block invoked, ret is 1
finallyThrowException:1

 

观察输出结果会发现,主方法并没有捕获到finallyThrowException方法调用时的异常(catch块的打印没有执行)。

这两个方法的主要区别也是在于:在finallyThrowException方法的finally块中多出了return ret语句。调用finallyThrowException方法的执行过程同调用throwException方法基本一致。

  1. finallyThrowException方法执行时,因为除0操作抛出异常,程序进入catch块,首先执行打印输出:catch block / by zero
  2. 接下来会执行catch块的throw e语句,向上抛出异常,而finally语句又是必须执行的,此时程序会先执行finally块。
  3. 进入finally块后会输出:finally block invoked!!! 和finally block invoked, ret is 1
  4. finally块执行到return ret时,该方法直接返回了ret的值,
  5. 在main方法中得到finallyThrowException的返回值后输出:finallyThrowException:1

finallyThrowException方法执行结果可以看出方法执行时的异常被丢失了


最后再来看一个小例子

 1 public static void finallyWork(){
 2         int count = 0;
 3         while(true){
 4             try{
 5                 if(count++ == 0){
 6                     throw new Exception("my error");
 7                 }
 8                 System.out.println("invoked ...");
 9             }catch(Exception e){
10                 System.out.println("catched exception:" + e.getMessage());            
11             }finally{
12                 System.out.println("finally block invoked!!!");
13                 if(count == 2){
14                     break;
15                 }
16             }
17         }
18     }

这个小例子的主要思路是当java中的异常不允许我们回到异常抛出的地点时,我们可以将try块放到循环里,这样程序就又可以回到异常的抛出点了,可以同时设置一个计数器,当累积尝试一定的次数后程序就退出。

ok,就说这么多了,下面附上完整代码:

package tt;

public class FinallyWorks {

    /**
     * @param args
     */
    public static void main(String[] args) {
         
        //finallyWork();
        /*
         *<output begin>
         *        catch block / by zero
         *        finally block invoked!!!
         *        finally block invoked, ret is 1
         *          throwReturn:0
         *</output end>
         *从输出结果中可以看出程序在int temp = 10/0;这一行抛出异常,直接进入catch块,首先输出打印catch block...,继续往下执行时碰到return语句,由于程序
         *存在finally语句,在程序返回之前需要执行finally语句。那么此时程序会将return的结果值暂时存起来,继续执行finally,从输出上可以看出finally执行后ret
         *的值变为了1,而整个方法最终的返回结果是0,说明return的是之前暂存的值。
         * */
        //System.out.println("throwReturn:" + throwReturn());
        
        /*
         * <output begin>
         *        catch block / by zero
         *        finally block invoked!!!
         *        finally block invoked, ret is 1
         *          finallyReturn:1
         *</output end>
         *从输出结果中可以看出程序在int temp = 10/0;这一行抛出异常,直接进入catch块,首先输出打印catch block...,继续往下执行时碰到return语句,由于程序
         *存在finally语句,在程序返回之前需要执行finally语句。那么此时程序会将return的结果值暂时存起来,继续执行finally,从输出上可以看出finally执行后ret
         *的值变为了1,有在finally块中碰到了return语句,方法就直接返回了,所以方法结果返回了1。
         * */
        //System.out.println("finallyReturn:" + finallyReturn());
        
        /*
         *<output begin>
         *        catch block / by zero
         *        finally block invoked!!!
         *        finally block invoked, ret is 1
         *          捕获到throwException方法抛出的异常,/ by zero
         *</output end>
         *从输出结果中可以看出在调用throwException方法是出现异常,程序进入该方法的catch块中,输出:catch block / by zero
         *由于存在finally,程序会先执行完finally语句输出:finally block invoked!!! 和 finally block invoked, ret is 1
         *然后将捕获到的异常抛向上层。上层的main方法catch到这个异常之后会输出:捕获到throwException方法抛出的异常,/ by zero
         *《注意throwException:那句打印是不会输出的》
         * */
        
        /*try {
            System.out.println("throwException:" + throwException());
        } catch (Exception e) {
            System.out.println("捕获到throwException方法抛出的异常," + e.getMessage());
        }*/
        
        
        /*
         *<output begin>
         *           catch block / by zero
         *        finally block invoked!!!
         *        finally block invoked, ret is 1
         *          finallyThrowException:1
         *</output end>
         *从输出结果中可以看出在调用finallyThrowException方法是出现异常,程序进入该方法的catch块中,输出:catch block / by zero
         *由于存在finally,程序会先执行完finally语句输出:finally block invoked!!! 和 finally block invoked, ret is 1
         *之后程序执行到finally块中return语句,直接返回了ret的值,主方法接受到这个返回值后输出:finallyThrowException:1
         *《注意主方法中catch块代码并没有被执行,这就说明了finallyThrowException方法中异常被丢失了》
         * */
        try {
            System.out.println("finallyThrowException:" + finallyThrowException());
        } catch (Exception e) {
            System.out.println("捕获到finallyThrowException方法抛出的异常," + e.getMessage());
        }
    }
    
    public static int throwException() throws Exception{
        int ret = 0;
        try{
            ret = 10/0 ;
            System.out.println("ret:" + ret);
            return ret;
        }catch(Exception e){
            System.out.println("catch block " + e.getMessage());
            throw e;
        }finally{
            System.out.println("finally block invoked!!!");
            ret++;
            System.out.println("finally block invoked, ret is " + ret);
        }
        
    }
    
    public static int finallyThrowException() throws Exception{
        int ret = 0;
        try{
            ret = 10/0 ;
            System.out.println("ret:" + ret);
            return ret;
        }catch(Exception e){
            System.out.println("catch block " + e.getMessage());
            throw e;
        }finally{
            System.out.println("finally block invoked!!!");
            ret++;
            System.out.println("finally block invoked, ret is " + ret);
            return ret;
        }
        
    }
    
    public static int throwReturn(){
        int ret = 0;
        try{
            ret = 10/0 ;
            ret++;
            return ret;
        }catch(Exception e){
            System.out.println("catch block " + e.getMessage());
            //ret++;
            return ret;
        }finally{
            System.out.println("finally block invoked!!!");
            ret++;
            System.out.println("finally block invoked, ret is " + ret);
        }
        
    }
    
    public static int finallyReturn(){
        int ret = 0;
        try{
            ret = 10/0 ;
            ret++;
            return ret;
        }catch(Exception e){
            System.out.println("catch block " + e.getMessage());
            //ret++;
            return ret;
        }finally{
            System.out.println("finally block invoked!!!");
            ret++;
            System.out.println("finally block invoked, ret is " + ret);
            return ret;
        }
        
    }
    /**
     * 当java中的异常不允许我们回到异常抛出的地点时,我们可以将try块放到循环里,
     * 这样程序就又可以回到异常的抛出点了,可以同时设置一个计数器,
     * 当累积尝试一定的次数后程序就退出。
     */
    public static void finallyWork(){
        int count = 0;
        while(true){
            try{
                if(count++ == 0){
                    throw new Exception("my error");
                }
                System.out.println("invoked ...");
            }catch(Exception e){
                System.out.println("catched exception:" + e.getMessage());            
            }finally{
                System.out.println("finally block invoked!!!");
                if(count == 2){
                    break;
                }
            }
        }
    }

}

 

 

 

 

 

转载于:https://www.cnblogs.com/pengkw/archive/2012/11/22/2783342.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值