当前位置: 首页 > 科技观察

Java笔试面试总结——try、catch、finally语句有return的各种情况

时间:2023-03-12 16:57:01 科技观察

前言在写试题和面试之前,经常遇到或者被问到try-catch-finally语法块的执行顺序等等,今天抽空整理了一下这个知识点,然后记录下来。正文本文主要通过实例说明各种情况。这里我按照try-catch-finally语法块分为两种主要情况来讨论:try-catch语法块和try-catch-finally语句块,然后我们分情况详细讨论。1.try-catch语句块我们可以看下面的程序:publicstaticvoidmain(String[]args){System.out.println(handleException0());}/***try,catch都有return*@return*/privatestaticStringhandleException0(){try{System.out.println("开始尝试");Strings=null;intlength=s.charAt(0);System.out.println("结束尝试");return"try块的返回值";}catch(Exceptione){System.out.println("异常被捕获");return"catch的返回值";}}执行结果:try开始捕获异常catch返回值分析:程序首先执行try块如果在try块中发现异常,try块后面的代码会没有被执行(也不会自然返回),然后进入匹配异常的catch块,再进入catch块完成代码执行。当执行到catch中的return语句时,程序就终止了,然后返回这个return的最终结果。2.try-catch-finally语句块这个语法块分为4种情况进行讨论,下面我会一一列举。第一种情况,try块中有return,捕获异常1:publicstaticvoidmain(String[]args){Stringresult=handleException1();System.out.println(result);}privatestaticStringhandleException1(){try{System.out.println("trystart");Stringstr=null;intlength=str.length();System.out.println("tryend");}catch(Exceptione){System.out.println("catch到达异常");}finally{System.out.println("finallyblock执行完成");}return"finalresult";}示例1执行结果如下:trystartedcatchtheexceptionfinallyblockexecution完成并最终得到例2的结果:");Stringstr=null;intlength=str.length();System.out.println("tryend");return"try块的返回值";}catch(Exceptione){System.out.println(“捕获到一个异常”);}finally{System.out.println("finallyblock执行完成");}return"finalresult";}例子2执行结果如下:try开始捕获异常finallyblock执行完成最终结果分析:第一个例子1和例2结果很明显,遇到异常时到时候直接进入匹配的catch块,然后继续执行finally语句块,最后返回返回结果。第二种情况:try块中有return,但不会捕获到异常。例3:思考:下面的代码try语句块中有return语句,那么是否可以在执行完try语句块后直接返回并退出方法呢?publicstaticvoidmain(String[]args){Stringresult=handleException3();System.out.println(result);}privatestaticStringhandleException3(){try{System.out.println("");return"try块的返回值";}catch(Exceptione){System.out.println("捕获到异常");}finally{System.out.println("finallyblock执行完成");}return"finalresult";}执行结果例3的执行结果如下:finally块执行及try块的返回值分析:例3的结果其实可以通过break方式看程序的具体执行过程。通过断点我们可以发现代码先执行了try块中的代码。当return语句执行时,handleException3方法并没有立即结束,而是继续执行finally块。代码,finally块中的代码执行完后,返回到try块的return语句,然后返回最终结果,执行handleException方法。第三种情况:try块和finally中都有return例4:publicstaticvoidmain(String[]args){System.out.println(handleException4());}/***Case3:既有try又有finally有return*@return*/privatestaticStringhandleException4(){try{System.out.println("");return"try块的返回值";}catch(Exceptione){System.out.println("捕获到异常");}finally{System.out.println("finally块执行完成");return"finally的返回值";}//return"最终结果";//不能再有返回值了}例4的执行结果:finally块完成了finally返回值解析:需要注意的是当try块和finally中都有return时,在try/catch/finally语法块之外不允许使用return关键字。下面通过程序中的断点来看一下代码的具体执行流程。该代码首先执行try块中的代码。当return语句执行时,handleException4方法并没有立即结束,而是继续执行finally块中的代码。当在finally块中发现return时,直接将finally块中的return值(即最终结果)返回,执行handleException4方法。第四种情况:tryblock、catchblock、finallyblock都有return例5:publicstaticvoidmain(String[]args){System.out.println(handleException5());}/***Case4:try,catch,最后有return*@return*/privatestaticStringhandleException5(){try{System.out.println("trystart");int[]array={1,2,3};inti=array[10];System.out.println("尝试结束");return"try块的返回值";}catch(Exceptione){e.printStackTrace();//这行代码其实就是打印出异常的具体信息System.out.println("Exceptioncaught");return"catch返回值";}finally{System.out.println("finally块执行完成");return"最终返回值";}//return"最终结果";}示例5的执行结果:try捕获异常finally块执行完成finally返回值java.lang.ArrayIndexOutOfBoundsException:10atcom.example.javabasic.javabasic.ExceptionAndError.TryCatchFinally.handleException5(TryCatchFinally.java:25)atcom.example.javabasic.javabasic.ExceptionAndError.TryCatchFinally.main(TryCatchFinally.java:14)分析:程序首先执行try块中的代码,如果在try块中发现异常,try块后面的代码将不会执行(也不会自然返回),然后进入匹配异常的catch块,再进入catch块执行代码毕竟当catch中的return语句执行完后,程序并不会立即终止,而是会继续执行finally块中的代码,最后执行finally块中的return,然后返回最后的结果返回。其实我们通过上面的例子可以发现,不管return关键字在哪里,finally都一定会被执行。理论上,在try、catch、finally块中允许使用return关键字,但是执行优先级低的块中return关键字定义的返回值会覆盖执行优先级高的块中return关键字定义的return执行优先级值。也就是说finally块中定义的返回值会覆盖catch块和try块中定义的返回值;catch块中定义的返回值将覆盖try块中定义的返回值。也就是说,如果返回值是在finally块中通过return关键字定义的,那么之前所有通过return关键字定义的返回值都将无效——因为finally块中的代码必须被执行。本文经授权转载自公众号“良墟Linux”。世界500强外企Linux开发工程师梁旭,在公众号分享大量Linux干货,欢迎关注!