throw
throw 语句用于抛出异常,例如 throw new EOFException()。
 
throws
当使用throw 语句抛出checked 异常后,可以不用捕获异常并处理,而是使用throws 语句传递异常给本方法的调用者,调用者根据自身情况对异常进行捕获或者继续传递异常给它的调用者,如下:
public void read () throws IOException(
xxx
throw new IOException();
}
当调用了包含throws checked 异常语句的方法后,可以用同样方式处理。
 
try/catch
如果打算捕获并处理异常,那么可以使用 try/catch 语句块,一般格式如下:
try{
xxx
}
catch (IOException e){
xxx
}
catch (Exception e){
xxx
}
在Java SE 7中,也可以合并多个catch语句,如下:
try{
xxx
}
catch (IOException e | Exception e){
xxx
}
如果在 try 语句块中的任何代码抛出了一个在 catch 语句块中捕获的异常类,那么程序将跳过 try 语句块的其余代码并且执行对应 catch 语句块中的代码。如果方法中的任何代码拋出了一个在 catch 语句块中没有声明的异常类型,那么这个方法就会立刻退出。
catch 语句块在处理异常时,可以对异常进行包装后重新抛出,如下:
try{
xxx
}
catch (SQLException e){
throw new ServletException ("xxxx") ;
}
 
finally
不管try 语句块是否抛出异常,甚至在try 语句块里有return 语句,finally 语句块中的代码最后都会被执行。它通常用来回收系统资源,如下:
InputStream in = ..
try{
xxx
}
finally{
in.close();
}
也可以带有catch 语句块,如下:
InputStream in = ..
try{
xxx
}
catch (IOException e){
xxx
}
finally{
in.close();
}
注意,当执行了System.exit()、JVM崩溃、当前线程被其他线程中断或者杀死,那么finally 语句块不会执行。
 
return
return 是用来退出当前方法,并返回一个值给调用者。
 
综合
看一个例子:
public class Demo {
public static int test() {
int x = 1;
try {
return ++x;
} catch (Exception e) {
e.printStackTrace();
} finally {
++x;
}
return x;
}
 
public static void main(String[] args) throws Exception {
int y = test();
System.out.println(y);
}
}
 
以上例子中,最终输出2。
 
原因是什么?
翻看官方的jvm规范就会把一切的谜团解开了:
If the try clause executes a return, the compiled code does the following:
Saves the return value (if any) in a local variable.
Executes a jsr to the code for the finally clause.
Upon return from the finally clause, returns the value saved in the local variable.
简单翻译下:
如果try语句里有return,那么代码的行为如下:
1.如果有返回值,就把返回值保存到局部变量中
2.执行jsr指令跳到finally语句里执行
3.执行完finally语句后,返回之前保存在局部变量表里的值
根据上面的说明就可以轻易地解释为什么是2了。
当执行到return ++x;时,jvm在执行完++x后会在局部变量表里另外分配一个空间来保存当前x的值。
注意,现在还没把值返回给y,而是继续执行finally语句里的语句。等执行完后再把之前保存的值(是2不是x)返回给y。所以就有了y是2不是3的情况。
其实这里还有一点要注意的是,如果你在finally里也用了return语句,比如return +xx。那么y会是3。因为规范规定了,当try和finally里都有return时,会忽略try的return,而使用finally的return。
 
查看Test.class的字节码我们同样也可以很轻松地知道为什么是2而不是3:
大概讲讲指令操作顺序:
iconst_1: 把常数1进栈 ---> istore_1: 栈顶元素出栈并把元素保存在本地变量表的第二个位置里(下标为1的位置里) ---> iinc 1, 1 : 本地变量表的第二个元素自增1 --->iload_1:第二个元素进栈 ---> istore_2:栈顶元素出栈并把元素保存在本地变量表的第2个位置里 ---> iinc 1, 1 : 本地变量表的第二个元素自增1 ---> iload_2:第二个元素进栈 (注意,此时栈顶元素为2)---> ireturn:返回栈顶元素。
后面的指令是要在2-7行出现异常时在跳到12行的,这个例子没出现异常,不用关注。
上面流程栈和本地变量表的情况如下图:
 
 
 
参考
https://www.cnblogs.com/averey/p/4379646.html

throw throws try catch finally return的更多相关文章

  1. 【Java】异常 —— throw, throws, try catch 相关内容

    嗯……面试考到了这个,又是一个如无意外 那么接下来就总结吧 一.什么是异常 程序运行过程中发生的异常事件. RuntimeException通常是因为编程员因为疏忽没有检查而引起的错误. 二.Exce ...

  2. Java throw throws try...catch区别

    java里的异常多种多样,这是一种非常有用的机制,它能帮助我们处理那些我们未知的错误,在java里,关于异常的有throw throws,还有一个try catch 程序块.接下来我们挨个看看这几个的 ...

  3. 异常处理(throw,throws,try,catch,finally)

    一.异常 1.定义:程序在运行时出现的不正确的情况. 2.由来:问题也是生活中的事物,也可以被Java描述,并被封装成对象. 其实就是Java对不正常情况进行描述后的对象体现. 3.划分:Java对于 ...

  4. final finalize finally throw throws try catch

    什么是finalize()方法 finalize()方法什么时候被调用 参见网址 析构函数(finalization)的目的是什么 final 和 finalize 的区别 final以下参见网址 f ...

  5. java异常处理之throw, throws,try和catch

    转自 http://blog.csdn.net/zhouyong80/article/details/1907799  程序运行过程中可能会出现异常情况,比如被0除.对负数计算平方根等,还有可能会出现 ...

  6. 顺平讲try catch finally throw throws(精华)

    try catch finally  有点像if else语句 还有像javascript的服务器执行成功后的回调函数,success:function(){ 进行处理 }; throws的意思是将异 ...

  7. throws、throw和try catch

    在学习代理模式的时候,编写动态生成代理类.java文件时,用try{}catch(){}捕获异常发现catch(Exception e)报错,得换成catch(Throwable e),然后又查了查两 ...

  8. java:异常机制(try,catch,finally,throw,throws,自定义异常)

    * String类中的格式化字符串的方法: * public static String format(String format, Object... args):使用指定的格式字符串和参数返回一个 ...

  9. try-catch和throw,throws的区别

    java里的异常多种多样,这是一种非常有用的机制,它能帮助我们处理那些我们未知的错误,在java里,关于异常的有throw throws,还有一个try catch 程序块.接下来我们挨个看看这几个的 ...

随机推荐

  1. .net core 3.0 web api 重点设置,主要为了解决axios post不到参数问题

    这两天研究.net core 3.0升级,前端vue+axios 后端web api.测试过程中发现post的时候,由于提交的是json对象,后端web api获取不到数据. 今天贴了下解决过程.主要 ...

  2. [FJOI2020]染色图的联通性问题 题解

    FJOI2020 D1T2 题目大意 给出一个由 $n$ 个点 $m$ 条边构成的染色无向图,求删去每一个点及与其相连的边后图中不连通的同色点对数量.$n,m\leq 10^5$. 思路分析 可以想到 ...

  3. 基于Appium的UI自动化测试

    为什么需要UI自动化测试 移动端APP是一个复杂的系统,不同功能之间耦合性很强,很难仅通过单元测试保障整体功能.UI测试是移动应用开发中重要的一环,但是执行速度较慢,有很多重复工作量,为了减少这些工作 ...

  4. 洛谷P1080 国王游戏 python解法 - 高精 贪心 排序

    洛谷的题目实在是裹脚布 还编的像童话 这题要 "使得获得奖赏最多的大臣,所获奖赏尽可能的少." 看了半天都觉得不像人话 总算理解后 简单说题目的意思就是 根据既定的运算规则 如何排 ...

  5. 使用Loadrunner进行性能测试

    一.确定性能测试的范围.要求.配置.工具等 明确测试的系统: 本文档主要指的是web应用. 明确测试要求: 用户提出性能测试,例如,网站首页页面响应时间在3S之内,主要的业务操作时间小于10s,支持3 ...

  6. HDU - 1261-字串数 (排列组合+大数)

    一个A和两个B一共可以组成三种字符串:"ABB","BAB","BBA". 给定若干字母和它们相应的个数,计算一共可以组成多少个不同的字符串 ...

  7. Mybatis实例增删改查(二)

    创建实体类: package com.test.mybatis.bean; public class Employee { private Integer id; private String las ...

  8. js reduce

    数组对象求和 let books = [ { id: 100, name: '红楼梦', price: 100 }, { id: 101, name: '西游记', price: 150 }, { i ...

  9. idea报错cannot resolve symbol servlet

    解决方法:在project structure中导入包.该包在tomcat安装目录的lib文件夹.导入之后点击Apply.

  10. 【Java/DateTime】用当前日期时间与确定日期时间比较,大于则执行某动作

    代码: package logbackCfg; import java.text.ParseException; import java.text.SimpleDateFormat; import j ...