java中return和throws exception的选择

虎三儿 2015-06-17 01:47:15
各位大侠,本人最近一直在纠结,在处理具体的业务逻辑的时候,通过return和抛出异常都可以实现程序的终止执行,那么在项目的实际操作过程中,什么时候采用return,什么时候采用抛出异常合适呢?
...全文
1226 33 打赏 收藏 转发到动态 举报
AI 作业
写回复
用AI写文章
33 条回复
切换为时间正序
请发表友善的回复…
发表回复
虎三儿 2015-06-23
  • 打赏
  • 举报
回复
引用 30 楼 xiakepan 的回复:
可能存在这种情况,能用代码控制的逻辑,就是正常的流程。比如登陆成功、失败,这都是正常的流程,使用return。 能用代码逻辑处理的,譬如空指针,数组越界等,都实现判断是否存在,存在是存在的逻辑,不存在是不存在的逻辑,这里我也是使用的return。 其他的不可预见的错误,我也不知道的,就让他throw吧,在最外层方法catch中打印下日志,然后return。 ---------------------------------------然并卵的分割线----------------------------------------- 简而言之,逻辑都是return控制,try-catch就是抓异常打错误日志辅助逻辑控制的。 上面是我平时的处理方法。欢迎来喷。 ps:貌似我也是有理论依据的,有个先人曾告诉me:try-catch这样的情况虚拟机都采用异常机制去处理,如果如果访问量过高死都不知道是怎么死的。
其实你的处理情况和我是一样的,但是我在项目中常常看到其他人直接throw我用return方式处理的逻辑,比如如你所说的“正常流程”,他们的处理方式很简单,只要不满足我的要求都是不正常的流程,我就用异常去结束程序,这样service中抛出的异常在action中也不用在处理了,直接定位到错误页面即可。其实也是有道理的,也是我看了以后觉得迷惑的地方。异常不能滥用,我也不知道他们这种方式是否叫滥用异常
番茄鲨鱼面 2015-06-23
  • 打赏
  • 举报
回复
可能存在这种情况,能用代码控制的逻辑,就是正常的流程。比如登陆成功、失败,这都是正常的流程,使用return。 能用代码逻辑处理的,譬如空指针,数组越界等,都实现判断是否存在,存在是存在的逻辑,不存在是不存在的逻辑,这里我也是使用的return。 其他的不可预见的错误,我也不知道的,就让他throw吧,在最外层方法catch中打印下日志,然后return。 ---------------------------------------然并卵的分割线----------------------------------------- 简而言之,逻辑都是return控制,try-catch就是抓异常打错误日志辅助逻辑控制的。 上面是我平时的处理方法。欢迎来喷。 ps:貌似我也是有理论依据的,有个先人曾告诉me:try-catch这样的情况虚拟机都采用异常机制去处理,如果如果访问量过高死都不知道是怎么死的。
虎三儿 2015-06-23
  • 打赏
  • 举报
回复
讨论看来还是没有结果呀。大神们,求指点
乱世丶桃花 2015-06-23
  • 打赏
  • 举报
回复
这个问题只可意会,不可言传
hepeng_8 2015-06-23
  • 打赏
  • 举报
回复
业务的返回还是使用retrurn 如果是项目中的异常使用Exception。
无极丶 2015-06-19
  • 打赏
  • 举报
回复
而且我觉得return一般用在js上。java的return强制结束不经常见。
无极丶 2015-06-19
  • 打赏
  • 举报
回复
return说明你这个方法是有返回类型的。举个例子:如果你用的throw 或者throws 没出现异常就return你的值 出现了就向上抛。一般用throw的都是让别人调用的方法 。 a用的throws b调用a 那么b用try catch就捕捉到了,如果还想向上抛,继续throws
开拓者Amadues 2015-06-19
  • 打赏
  • 举报
回复
引用 27 楼 wenbin516 的回复:
而且我觉得return一般用在js上。java的return强制结束不经常见。
return就是返回而已,作用和throw差不多的。 只不过在上层方法里对于throw可以捕获,对于return要手动处理。
finemi 2015-06-18
  • 打赏
  • 举报
回复
引用 6 楼 biaogexiangjia 的回复:
对,你的猜想很正确了。 一般来说,设计类库或者框架,需要严格完善的使用异常机制,因为尤其是框架,往往一个地方出错会引发后面很多使用上出现错误 这就涉及到一个异常设计原则:将会导致以后相关功能出错,或者无法通过参数检查时,立即抛出错误。 前者比如:一个类需要一个filename参数,而这个类同时有一个save()方法,那么显然当传入的filename如果是一个非法的路径,执行save()方法时就会出现错误,那么在传入filename参数的地方,就必须使用异常来明确的指出这是一个错误。 后者比较好理解:因为一个方法的调用者,肯定清除的知道所调用的方法的参数的要求,不符合要求就可以立即抛出异常。 以上的也只是异常的一种设计原则罢了,实际上还有很多原则,他们之间难免还有出现一些矛盾的情况。 而我个人的经验及建议就是,对于web开发中,通常只有Dao层会调用JDK API或者其他框架产生异常,捕获后记录日志直接抛出或者直接throws申明,因为本身自己也确实不知道怎么处理最后还是会返回到view显示给用户,各种集中处理异常的方法也很多比较方便。而业务层通常来说是不会有自己的异常产生,可以定义一个返回值接口及各种实现类,包含是否执行成功、错误代码、错误信息等 以上是个人见解
zn85600301 2015-06-18
  • 打赏
  • 举报
回复
正常处理完成 return 异常退出 throw exception
虎三儿 2015-06-18
  • 打赏
  • 举报
回复
引用 17 楼 shijing266 的回复:
[quote=引用 16 楼 biaogexiangjia 的回复:] [quote=引用 14 楼 shijing266 的回复:] 那么纠结... 如果你的service方法需要返回一个实体对象什么,这个对象是你需要用到的对象,那么这个时候,建议throw 一个异常 如果你的方法只是单纯的void ,你return 也没啥错,不过如果还有后续方法的话,就会继续执行,如果需要强制中断的话,建议还是throw 如果需要继续执行下面的方法体,那就用return吧
throw确实是可以偷懒,强制中断,在它的上层可以阻断程序的继续执行;若单纯的终止程序的话也不用根据返回结果来再一次的return,但是问题在于抛出的异常是否合理?不能单纯的为了终止程序而抛出异常吧?[/quote] 那肯定啊,为啥要自定义异常? 不就是为了你的业务逻辑吗? 在需要的地方throw exception ,然后你的调用者去捕获,去做其他的逻辑处理 , 一般这种方式用在service层的校验上面,或者你service方法里面 有个多层循环,这个时候出现了不可避免的逻辑校验,return 是没用的,throw 一个异常,对程序的处理也方便,也不影响你项目的使用[/quote] 同意。特别对多层循环的例子,用异常确实更方便。自定义异常确实能定制符合自己需求的不合法逻辑处理。那你的意思就是说,如果能用自定义异常反应代码问题,就不用return,直接抛出自定义异常吗?
虎三儿 2015-06-18
  • 打赏
  • 举报
回复
引用 11 楼 u012906938 的回复:
[quote=引用 5 楼 biaogexiangjia 的回复:] [quote=引用 3 楼 u012906938 的回复:] 单纯地throws Exception或者return其实是对异常的一种不负责任的行为,当你觉得你的代码块会出现异常时,最好使用try catch去捕捉异常,譬如有IO流的操作代码块,不仅使用try catch去捕捉,而且最后还要用finally去关闭流。 在你提到的用户登陆错误的问题中,如果你用try catch去捕捉异常,然后你发现了用户登陆错误,那么你就应该在catch模块中对异常进行处理了,譬如可以用logger记录下错误,然后再选择需要返回什么信息与页面给用户,当然用户并不知道你后台进行了什么处理,如果这时候登陆报错了,你什么都不做来个return,那服务器那边就出来个500错误是吧 关于这个异常处理,关键还是要知道程序会出什么异常,当然还可以用一些自定义异常类来使自己的代码严谨一点。
我的意思是程序中如果使用return的方式终止程序的执行,那么就不存在异常处理的问题了,此时不抛出异常直接用return的方式告诉调用者一个结果,这种情况下,调用者也不用处理异常了,根据返回的结果做相应的处理即可;若直接抛出异常,在调用者势必会捕获着个 异常,那么此时的处理情况就不是拿返回值,而是针对这个抛出的异常做对应的处理了。 疑问在于在可以抛出异常和通过return的方式终止程序执行的适合,如何去选择是通过return还是throw的形式。[/quote] 这有什么好纠结的,你就是想太多了,不管工作多少年,你保证你的程序正常运行少出BUG,那你就是一个好的程序员。你的问题是程序出错了,到底是return还是throw,那么你自己想想如用return调用者得到什么,用throw调用者又得到什么?你的程序用了它们之后访问是否友好?如果你说别人调用你的接口,他只想得到1或者0,那不管你程序出什么错,你都还是只需要决返回1还是0给他,对吧?如果你的方法或者接口就只是自己用的,那么你return还是throw没人会在乎,一个空指针异常也不会导致系统崩溃,当然还是得对错误负责点,多分析逻辑。不管你return还是throw,业务能正常处理,程序能正常结束即可,这只是我个人的理解。[/quote] 这样理解也对,不管用何种方式只要能正常结束程序即可。我们现在探讨的不是用何种方式去正常结束程序更好吗?感谢指教!
  • 打赏
  • 举报
回复
引用 16 楼 biaogexiangjia 的回复:
[quote=引用 14 楼 shijing266 的回复:] 那么纠结... 如果你的service方法需要返回一个实体对象什么,这个对象是你需要用到的对象,那么这个时候,建议throw 一个异常 如果你的方法只是单纯的void ,你return 也没啥错,不过如果还有后续方法的话,就会继续执行,如果需要强制中断的话,建议还是throw 如果需要继续执行下面的方法体,那就用return吧
throw确实是可以偷懒,强制中断,在它的上层可以阻断程序的继续执行;若单纯的终止程序的话也不用根据返回结果来再一次的return,但是问题在于抛出的异常是否合理?不能单纯的为了终止程序而抛出异常吧?[/quote] 那肯定啊,为啥要自定义异常? 不就是为了你的业务逻辑吗? 在需要的地方throw exception ,然后你的调用者去捕获,去做其他的逻辑处理 , 一般这种方式用在service层的校验上面,或者你service方法里面 有个多层循环,这个时候出现了不可避免的逻辑校验,return 是没用的,throw 一个异常,对程序的处理也方便,也不影响你项目的使用
虎三儿 2015-06-18
  • 打赏
  • 举报
回复
引用 14 楼 shijing266 的回复:
那么纠结... 如果你的service方法需要返回一个实体对象什么,这个对象是你需要用到的对象,那么这个时候,建议throw 一个异常 如果你的方法只是单纯的void ,你return 也没啥错,不过如果还有后续方法的话,就会继续执行,如果需要强制中断的话,建议还是throw 如果需要继续执行下面的方法体,那就用return吧
throw确实是可以偷懒,强制中断,在它的上层可以阻断程序的继续执行;若单纯的终止程序的话也不用根据返回结果来再一次的return,但是问题在于抛出的异常是否合理?不能单纯的为了终止程序而抛出异常吧?
虎三儿 2015-06-18
  • 打赏
  • 举报
回复
引用 12 楼 qq_16216221 的回复:
我的理解是:throws是软处理,它可以捕获你代码块潜在的错误,并给予错误信息的提示,以及对应的处理方式,是一种友好的,帮助我们管理程序的方式; return是硬处理:这是我们人为的根据已知结果作为条件,来加到程序中做终止程序运行的方式。 比如:你说的用户登录情况,结果是已知的:如果经查询数据库用户登入的用户名不存在,就直接return了,然后前台根据return的值,来做友好的提示:用户名不存在,请注册。 云云... 对于程序在JVM中跑,可能存在未知的情况,这时就需要try catch捕获异常了,用throws抛出。
那是否可以理解为,如果处理的结果已知,那么就可以直接return,而不用异常?
  • 打赏
  • 举报
回复
那么纠结... 如果你的service方法需要返回一个实体对象什么,这个对象是你需要用到的对象,那么这个时候,建议throw 一个异常 如果你的方法只是单纯的void ,你return 也没啥错,不过如果还有后续方法的话,就会继续执行,如果需要强制中断的话,建议还是throw 如果需要继续执行下面的方法体,那就用return吧
虎三儿 2015-06-18
  • 打赏
  • 举报
回复
引用 9 楼 finemi 的回复:
很感谢前辈能在凌晨还给予解答。 在正常的web开发过程中,几乎都脱离不了Action-service-dao三层的嵌套处理,根据前辈所说的异常处理原则,如果在action中捕获的一个参数,完全可能导致后续的service和dao的错误,那么此时在action中需要用异常来表示参数问题吗?因为参数合法性问题这个东西在一些情况下是可以预估的,如果能预先判断该参数是有问题的,那么在问题出现之初就应该加以处理,也就是在action中就终止程序的执行;对于前辈说的,dao中抛出的异常应该是在第一步参数问题解决之后出现的一些和参数无关的异常,确实可以通过直接抛出异常的方式去处理。 dao中抛出了异常,在service中会捕获,此时service捕获dao的异常又有两种处理方式:将异常直接throw;处理掉该异常;如果处理掉由dao中抛出的异常,那么应该是用return的方式将service的返回值反馈给Action了?若直接抛给Action,那么action必须对该异常做出反应。这里又有一个谁处理异常的问题。 service中通常需要通过查询去获取dao中数据数据作为参数,此时完全可能返回的数据为空或者数据不符合处理逻辑,这也可以理解为参数有误吧,完全有可能造成service后续步骤的问题,此时应异常还是return的方式呢? 个人的感觉,由于web的分层关系,dao必然执行的是和数据库相关的操作,出了问题确实不知道如何处理,抛出即可;service是逻辑处理的环节,此时应对dao的异常做出反应,处理掉该异常并用return的方式返回给action。也就说action中接收到的异常应该是和dao抛出的无关的异常;当然service自身也会出现异常的情况反馈给action做出反应。因此,action中处理service的异常,service处理dao的异常,dao直接抛出异常即可。action处于顶层,可以根据service层return的结果,或者异常信息反馈相应信息给客户端即可。 总结一下我的观点:service通过return的形式处理dao层的异常并反馈给action,用throw的形式处理自身异常。 请前辈们指点。
二十亩鱼 2015-06-18
  • 打赏
  • 举报
回复
我的理解是:throws是软处理,它可以捕获你代码块潜在的错误,并给予错误信息的提示,以及对应的处理方式,是一种友好的,帮助我们管理程序的方式; return是硬处理:这是我们人为的根据已知结果作为条件,来加到程序中做终止程序运行的方式。 比如:你说的用户登录情况,结果是已知的:如果经查询数据库用户登入的用户名不存在,就直接return了,然后前台根据return的值,来做友好的提示:用户名不存在,请注册。 云云... 对于程序在JVM中跑,可能存在未知的情况,这时就需要try catch捕获异常了,用throws抛出。
Coke-Code 2015-06-18
  • 打赏
  • 举报
回复
引用 5 楼 biaogexiangjia 的回复:
[quote=引用 3 楼 u012906938 的回复:] 单纯地throws Exception或者return其实是对异常的一种不负责任的行为,当你觉得你的代码块会出现异常时,最好使用try catch去捕捉异常,譬如有IO流的操作代码块,不仅使用try catch去捕捉,而且最后还要用finally去关闭流。 在你提到的用户登陆错误的问题中,如果你用try catch去捕捉异常,然后你发现了用户登陆错误,那么你就应该在catch模块中对异常进行处理了,譬如可以用logger记录下错误,然后再选择需要返回什么信息与页面给用户,当然用户并不知道你后台进行了什么处理,如果这时候登陆报错了,你什么都不做来个return,那服务器那边就出来个500错误是吧 关于这个异常处理,关键还是要知道程序会出什么异常,当然还可以用一些自定义异常类来使自己的代码严谨一点。
我的意思是程序中如果使用return的方式终止程序的执行,那么就不存在异常处理的问题了,此时不抛出异常直接用return的方式告诉调用者一个结果,这种情况下,调用者也不用处理异常了,根据返回的结果做相应的处理即可;若直接抛出异常,在调用者势必会捕获着个 异常,那么此时的处理情况就不是拿返回值,而是针对这个抛出的异常做对应的处理了。 疑问在于在可以抛出异常和通过return的方式终止程序执行的适合,如何去选择是通过return还是throw的形式。[/quote] 这有什么好纠结的,你就是想太多了,不管工作多少年,你保证你的程序正常运行少出BUG,那你就是一个好的程序员。你的问题是程序出错了,到底是return还是throw,那么你自己想想如用return调用者得到什么,用throw调用者又得到什么?你的程序用了它们之后访问是否友好?如果你说别人调用你的接口,他只想得到1或者0,那不管你程序出什么错,你都还是只需要决返回1还是0给他,对吧?如果你的方法或者接口就只是自己用的,那么你return还是throw没人会在乎,一个空指针异常也不会导致系统崩溃,当然还是得对错误负责点,多分析逻辑。不管你return还是throw,业务能正常处理,程序能正常结束即可,这只是我个人的理解。
finemi 2015-06-18
  • 打赏
  • 举报
回复
别想太多了,这个东西是很难讨论出来的,多做项目总结经验,具体情况具体分析,现在先找一个最简单方便的做就是了
加载更多回复(13)

67,543

社区成员

发帖
与我相关
我的任务
社区描述
J2EE只是Java企业应用。我们需要一个跨J2SE/WEB/EJB的微容器,保护我们的业务核心组件(中间件),以延续它的生命力,而不是依赖J2SE/J2EE版本。
社区管理员
  • Java EE
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧