throw和throws的区别以及try,catch,finally在有return的情况下执行的顺序
一,抛出异常有三种形式,一是throw,一个throws,还有一种系统自动抛异常。下面它们之间的异同。
(1)、系统自动抛异常
1.当程序语句出现一些逻辑错误、主义错误或类型转换错误时,系统会自动抛出异常:
public static void main(String[] args) {
int a = 5, b =0;
System.out.println(5/b);
//function();
}
系统会自动抛出ArithmeticException异常。
2.
public static void main(String[] args) {
String s = "abc";
System.out.println(Double.parseDouble(s));
//function();
}
系统会自动抛出NumberFormatException异常。
(2)、throw
throw是语句抛出一个异常,一般是在代码块的内部,当程序出现某种逻辑错误时由程序员主动抛出某种特定类型的异常
public static void main(String[] args) {
String s = "abc";
if(s.equals("abc")) {
throw new NumberFormatException();
} else {
System.out.println(s);
}
//function();
}
运行时,系统会抛出异常:
Exception in thread "main" java.lang.NumberFormatException
(3)、throws
throws是方法可能抛出异常的声明。(用在声明方法时,表示该方法可能要抛出异常)
public void function() throws Exception{......}
当某个方法可能会抛出某种异常时用于throws 声明可能抛出的异常,然后交给上层调用它的方法程序处理
public class testThrows {
public static void function() throws NumberFormatException {
String s = "abc";
System.out.println(Double.parseDouble(s));
}
public static void main(String[] args) {
try {
function();
} catch (NumberFormatException e) {
System.err.println("非数据类型不能强制类型转换。");
//e.printStackTrace();
}
}
}
运行结果:
非数据类型不能强制类型转换。
(4)、throw与throws的比较
throws出现在方法函数头;而throw出现在函数体。
throws表示出现异常的一种可能性,并不一定会发生这些异常;throw则是抛出了异常,执行throw则一定抛出了某种异常对象。
两者都是消极处理异常的方式(这里的消极并不是说这种方式不好),只是抛出或者可能抛出异常,但是不会由函数去处理异常,真正的处理异常由函数的上层调用处理。
(5)、编程习惯
在写程序时,对可能会出现异常的部分通常要用try{...}catch{...}去捕捉它并对它进行处理;
用try{...}catch{...}捕捉了异常之后一定要对在catch{...}中对其进行处理,那怕是最简单的一句输出语句,或栈输入e.printStackTrace();
如果是捕捉IO输入输出流中的异常,一定要在try{...}catch{...}后加finally{...}把输入输出流关闭;
如果在函数体内用throw抛出了某种异常,最好要在函数名中加throws抛异常声明,然后交给调用它的上层函数进行处理。
二,try,catch,finally在有return的情况下执行的顺序
结论:
1、不管有木有出现异常,finally块中代码都会执行;
2、当try和catch中有return时,finally仍然会执行;
3、finally是在return后面的表达式运算后执行的(此时并没有返回运算后的值,而是先把要返回的值保存起来,管finally中的代码怎么样,返回的值都不会改变,任然是之前保存的值),所以函数返回值是在finally执行前确定的;
4、finally中最好不要包含return,否则程序会提前退出,返回值不是try或catch中保存的返回值。
举例:
情况1:
try{} catch(){}finally{} return;
显然程序按顺序执行。
情况2:
try{ return; }catch(){} finally{} return;
程序执行try块中return之前(包括return语句中的表达式运算)代码;再执行finally块,最后执行try中return;finally块之后的语句return,因为程序在try中已经return所以不再执行。
情况3:
try{ } catch(){return;} finally{} return;
程序先执行try,如果遇到异常执行catch块,
有异常:则执行catch中return之前(包括return语句中的表达式运算)代码,再执行finally语句中全部代码,最后执行catch块中return. finally之后也 就是4处的代码不再执行。
无异常:执行完try再finally再return.
情况4:
try{ return; }catch(){} finally{return;}
程序执行try块中return之前(包括return语句中的表达式运算)代码;再执行finally块,因为finally块中有return所以提前退出。
情况5:
try{} catch(){return;}finally{return;}
程序执行catch块中return之前(包括return语句中的表达式运算)代码;再执行finally块,因为finally块中有return所以提前退出。
情况6:
try{ return;}catch(){return;} finally{return;}
程序执行try块中return之前(包括return语句中的表达式运算)代码;
有异常:执行catch块中return之前(包括return语句中的表达式运算)代码;则再执行finally块,因为finally块中有return所以提前退出。
无异常:则再执行finally块,因为finally块中有return所以提前退出。
最终结论:
任何执行try 或者catch中的return语句之前,都会先执行finally语句,如果finally存在的话,如果finally中有return语句,那么程序就return了,所以finally中的return是一定会被return的,编译器把finally中的return实现为一个warning。
下面是个测试程序
public class FinallyTest
{
public static void main(String[] args) { System.out.println(new FinallyTest().test());;
} static int test()
{
int x = 1;
try
{
x++;
return x;
}
finally
{
++x;
}
}
}
结果是2。
分析:
在try语句中,在执行return语句时,要返回的结果已经准备好了,就在此时,程序转到finally执行了。 在转去之前,try中先把要返回的结果存放到不同于x的局部变量中去,执行完finally之后,在从中取出返回结果, 因此,即使finally中对变量x进行了改变,但是不会影响返回结果。 它应该使用栈保存返回值。
参考博客:
https://blog.csdn.net/hjfcgt123/article/details/53349275
https://blog.csdn.net/kavensu/article/details/8067850
throw和throws的区别以及try,catch,finally在有return的情况下执行的顺序的更多相关文章
- JAVA之旅(十)——异常的概述,Try-Catch,异常声明Throws,多异常处理,自定义异常,Throw和Throws的区别
JAVA之旅(十)--异常的概述,Try-Catch,异常声明Throws,多异常处理,自定义异常,Throw和Throws的区别 不知不觉,JAVA之旅这个系列已经更新到第十篇了,感觉如梦如幻,时间 ...
- java基础之自定义异常类及throw和throws的区别
一.异常的架构: Throwable类:所以异常类都是Throwable的子类,它派生两个子类 Error和Exception. Error类:表示仅靠程序本身无法恢复的的严重错误,比如内存溢出,虚拟 ...
- Java 创建用户异常类、将异常一直向上抛、 throw和throws的区别
如果java提供的系统异常类型不能满足程序设计的需求,那么可以设计自己的异常类型. 从java异常类的结构层次可以看出,java类型的公共父类为Throwable.在程序运行中可能出现俩种问题:一种是 ...
- 异常机制及throw与throws的区别(转)
异常机制及throw与throws的区别 分类: Java2008-11-14 16:08 9672人阅读 评论(5) 收藏 举报 exceptionstringjavafunclass编译器 Jav ...
- java异常和throw和throws的区别
之前在编程中编译完成后,运行时,会遇见一些常见的错误,如NullPointerException,ArrayIndexOutOfBoundsException等等 在今天重新回顾学习了java异常,总 ...
- java中throw和throws的区别
throw和throws的区别: throws 用在方法声明后面,跟的是异常类名 可以跟多个异常类名,用逗号隔开 表示抛出异常,由该方法的调用者来处理 throws表示出现异常的一种可能性,并不一定会 ...
- Java中的throw和throws的区别
Java中的throw和throws的区别 1.throw关键字用于方法体内部,而throws关键字用于方法体部的方法声明部分: 2.throw用来抛出一个Throwable类型的异常,而throws ...
- Java 面向对象 异常处理:RunTimeexception,try-catch,异常声明throws,自定义异常,throw和throws的区别,多异常处理(9)
Java 面向对象 异常处理:RunTimeexception,try-catch,异常声明throws,自定义异常,throw和throws的区别,多异常处理(9)
- throw与throws的区别
throws语句 throws总是出现在一个函数头中,用来标明该成员函数可能抛出的各种异常.对大多数Exception子类来说,Java 编译器会强迫你声明在一个成员函数中抛出的异常的 ...
随机推荐
- 阿里微服务架构下分布式事务解决方案-GTS
虽然微服务现在如火如荼,但对其实践其实仍处于初级阶段.即使互联网巨头的实践也大多是试验层面,鲜有核心业务系统微服务化的案例.GTS是目前业界第一款,也是唯一的一款通用的解决微服务分布式事务问题的中间件 ...
- ASP.NET Core 实战:使用 NLog 将日志信息记录到 MongoDB
一.前言 在项目开发中,日志系统是系统的一个重要组成模块,通过在程序中记录运行日志.错误日志,可以让我们对于系统的运行情况做到很好的掌控.同时,收集日志不仅仅可以用于诊断排查错误,由于日志同样也是大量 ...
- Java进阶篇设计模式之七 ----- 享元模式和代理模式
前言 在上一篇中我们学习了结构型模式的组合模式和过滤器模式.本篇则来学习下结构型模式最后的两个模式, 享元模式和代理模式. 享元模式 简介 享元模式主要用于减少创建对象的数量,以减少内存占用和提高性能 ...
- 微服务(入门一):netcore安装部署consul
环境准备 vs开发环境:vs2017 consul版本: 1.4.4 netcore版本:2.1 安裝Consul 1.从官网下载consul到本地,选择系统对应的版本进行下载到本地,下载地址:h ...
- 4.JAVA-数组、String详解
1.数组 public class Test{ public static void main(String args[]){ int[] intArray = new int[] {1,4,3,2, ...
- 六大设计原则(一)SRP单一职责原则
单一职责原则SRP(Single reponsibility principle) BO(Business Object):业务对象 Biz(Business Logic):业务逻辑 SRP最简单的例 ...
- arcgis api 4.x for js 离线部署
在我的GIS之家群里,经常遇到 webgis 开发新手们提问 arcgis api for js 如何本地离线部署,而不是直接调用在线的,因为在线模式依赖互联网以及网速环境因素,受到的限制影响比较大. ...
- [ gczdac ] 20190306 访者必阅
1.我的私人博客!!! 2.博主还处于入门学习阶段,并且非常玻璃心 3. 激烈讨论√ 人身攻击× 4. 欢迎指正错误,相互学习 5. 很少在线,无法及时回复请谅解 https://www.cnblo ...
- 【死磕 Spring】----- IOC 之深入理解 Spring IoC
在一开始学习 Spring 的时候,我们就接触 IoC 了,作为 Spring 第一个最核心的概念,我们在解读它源码之前一定需要对其有深入的认识,本篇为[死磕 Spring]系列博客的第一篇博文,主要 ...
- MySQL 查询重复数据,删除重复数据保留id最小的一条作为唯一数据
开发背景: 最近在做一个批量数据导入到MySQL数据库的功能,从批量导入就可以知道,这样的数据在插入数据库之前是不会进行重复判断的,因此只有在全部数据导入进去以后在执行一条语句进行删除,保证数据唯一性 ...