`
accphc
  • 浏览: 125772 次
  • 性别: Icon_minigender_1
  • 来自: CD
社区版块
存档分类
最新评论

老掉牙的话题,java的异常处理。

阅读更多

关于系统中的异常怎么处理,之前也看过很多的文章。只是觉得越看越糊涂,大家持很多不同的意见。

现在想形成一套自己的观点,合自己口味的解决方案。没有对与不对,因人而宜。

 

DataAccessException extends RuntimeException  Dao层异常

ServiceException extends RuntimeException   Service层异常

我被java的RuntimeException和Exception的使用一直弄得头晕。
现在的观点是,把Exception转化成RuntimeException,省的方法还throws,个人觉得的throws看起来不爽,呵呵。
这就相当于在自己写代码过程中放弃了使用Exception。减少烦恼

但是有些自己写的工具类当中又是怎么处理呢。抛还是不抛(通过返回值),抛什么?

 

欢迎大家发表下意见,批评改正。

 

分享到:
评论
88 楼 carlkkx 2011-03-19  
pufan 写道
carlkkx 写道
其实你举得关于checked exception的例子都是异常滥用。

异常的妙处在于可以与返回值同时存在!
你还不明白的话我真无话可说了。

你现在也只是不承认滥用而已,你可能认为你这是妙用,但是你已经基本承认你举的checked exception已经不是异常本身的意义了。
87 楼 pufan 2011-03-19  
carlkkx 写道
API设计者要求你处理你就要处理
————————————————
这就回到我上面说的根本理念上了:
这个理念的核心是:API设计者没有资格要求。
看我上面写的这句话:
异常处理的选择权永远在使用方,被使用方不能越俎代庖,被使用方的职责就是要么完成目标要么报告错误,除此以外不要多管闲事。


“这个理念的核心是:API设计者没有资格要求。”恰恰相反,API设计者完全有必要提醒你有非常重要的异常可能会抛出,你一定要处理。

“被使用方的职责就是要么完成目标要么报告错误”这句话有问题,还应包括“要么向上抛出”,就好比我刚才举的IOException。

86 楼 carlkkx 2011-03-19  
pufan 写道
carlkkx 写道
另外我的客户端如果要和server通信那是明确的,你要获得某个server的连接,但是这通常是被配置的,我们先不管这个,假设你获得了server的连接,那么你要和server通信怎么办呢?
连接上提供了足够的通信机制,我们看一下例子:
connection.requestRemoteService("服务名", para, new CommonMsgCallback() {

            public void onMessage(CommonMsg msg) {

            }

connection.requestRemoteService("服务名", para, new CommonMsgSwingCallback() {

            public void onSwingMessage(CommonMsg msg) {

            }

CommonMsg msg = connection.syncRequestRemoteService("服务名",para);


我想问一下你,在我举得例子里面,你会不知道你在和server通信吗?上面举得三个通信方法都是请求响应模式,其实还有一些变种可以指定这次通信的超时等。第一第二个都是异步的,第二个的好处是如果消息的回应处理需要设置到GUI,那么onSwingMessage已经是EDT线程安全的。
第三个就是同步请求响应。
当然connection还有注册监听模式的通信方式。再我目前构建Swing客户端世界里,我是难以想象一个人最后要通过异常来判断是不是一个耗时的操作。

作为一个大型桌面应用来说,不仅仅与服务器通信这么一个api,更高层次的对象的获取增删改,以及在这之上的各种业务封装非常常见。举个例子吧:
City getCityByID(int id)这个方法,如果city是字典库设计(即完全本地内存cache)与非字典库设计(直接远程获取)在方法名上是看不出耗时的,不同过IO Exception提示的话,调用者很可能出EDT问题,特别是其他更加复杂的对象以及对象间的操作及调用封装的话情况更是如此。

别老是用大型这个词,这里你说的问题都是你想屏蔽一些你屏蔽不了的差异带来的。
85 楼 carlkkx 2011-03-19  
我要再次重申:这里有个关键理念不知道你认同不认同:
你的模块就是完成定义的目标,如果完成不了就报告错误,至于错误报告之后的事是不是不应该多管闲事?
如果你认同这个理念,那么checkedException就是错误的设计。

现在根据pufan兄的情况,我要再加一点,如果你认同这个理念但是还是用checkedException,说明你可能在滥用异常,即异常用于其他目的而不是异常本身的意义。
84 楼 pufan 2011-03-19  
carlkkx 写道
其实你举得关于checked exception的例子都是异常滥用。

异常的妙处在于可以与返回值同时存在!
你还不明白的话我真无话可说了。
83 楼 carlkkx 2011-03-19  
API设计者要求你处理你就要处理
————————————————
这就回到我上面说的根本理念上了:
这个理念的核心是:API设计者没有资格要求。
看我上面写的这句话:
异常处理的选择权永远在使用方,被使用方不能越俎代庖,被使用方的职责就是要么完成目标要么报告错误,除此以外不要多管闲事。
82 楼 pufan 2011-03-19  
carlkkx 写道
另外我的客户端如果要和server通信那是明确的,你要获得某个server的连接,但是这通常是被配置的,我们先不管这个,假设你获得了server的连接,那么你要和server通信怎么办呢?
连接上提供了足够的通信机制,我们看一下例子:
connection.requestRemoteService("服务名", para, new CommonMsgCallback() {

            public void onMessage(CommonMsg msg) {

            }

connection.requestRemoteService("服务名", para, new CommonMsgSwingCallback() {

            public void onSwingMessage(CommonMsg msg) {

            }

CommonMsg msg = connection.syncRequestRemoteService("服务名",para);


我想问一下你,在我举得例子里面,你会不知道你在和server通信吗?上面举得三个通信方法都是请求响应模式,其实还有一些变种可以指定这次通信的超时等。第一第二个都是异步的,第二个的好处是如果消息的回应处理需要设置到GUI,那么onSwingMessage已经是EDT线程安全的。
第三个就是同步请求响应。
当然connection还有注册监听模式的通信方式。再我目前构建Swing客户端世界里,我是难以想象一个人最后要通过异常来判断是不是一个耗时的操作。

作为一个大型桌面应用来说,不仅仅与服务器通信这么一个api,更高层次的对象的获取增删改,以及在这之上的各种业务封装非常常见。举个例子吧:
City getCityByID(int id)这个方法,如果city是字典库设计(即完全本地内存cache)与非字典库设计(直接远程获取)在方法名上是看不出耗时的,不同过IO Exception提示的话,调用者很可能出EDT问题,特别是其他更加复杂的对象以及对象间的操作及调用封装的话情况更是如此。
81 楼 carlkkx 2011-03-19  
其实你举得关于checked exception的例子都是异常滥用。
80 楼 carlkkx 2011-03-19  
pufan 写道
carlkkx 写道
走本地调用和远程调用一回事的路线的人本根不知道时间也是接口的一部分。

如何把时间放在接口内,传递Date?

你没有理解我的意思,这里要表达的意思是:本地调用和远程调用你无法屏蔽差异,因为一个东西对外的接口其实并不仅仅是逻辑意义上的还有时间,出错可能性等等。因为这些东西的不同导致你处理不同,事实上你们的情况就是一个扭曲的状况,一方面你们的API想方设法想要屏蔽差异,结果至少执行时间的差异你们无法屏蔽,然后呢这种差异又导致上面所谓处理不同(比如不能放在EDT),结果你们又用是否有IOException来判断这种差异。你说扭曲不扭曲?
79 楼 carlkkx 2011-03-19  
另外我的客户端如果要和server通信那是明确的,你要获得某个server的连接,但是这通常是被配置的,我们先不管这个,假设你获得了server的连接,那么你要和server通信怎么办呢?
连接上提供了足够的通信机制,我们看一下例子:
connection.requestRemoteService("服务名", para, new CommonMsgCallback() {

            public void onMessage(CommonMsg msg) {

            }

connection.requestRemoteService("服务名", para, new CommonMsgSwingCallback() {

            public void onSwingMessage(CommonMsg msg) {

            }

CommonMsg msg = connection.syncRequestRemoteService("服务名",para);


我想问一下你,在我举得例子里面,你会不知道你在和server通信吗?上面举得三个通信方法都是请求响应模式,其实还有一些变种可以指定这次通信的超时等。第一第二个都是异步的,第二个的好处是如果消息的回应处理需要设置到GUI,那么onSwingMessage已经是EDT线程安全的。
第三个就是同步请求响应。
当然connection还有注册监听模式的通信方式。在我目前构建的Swing客户端世界里,我是难以想象一个人最后要通过异常来判断是不是一个耗时的操作。
78 楼 pufan 2011-03-19  
carlkkx 写道
pufan 写道
carlkkx 写道
pufan 写道
carlkkx 写道
利用Checked Exception做业务流程分支设计比用返回值个人感觉更优雅
——————————————————————
晕倒,这已经是完全滥用异常了,程序执行的正常结果也用异常来表征了,如果我是调用者碰到这样的API我应该是难受死还哪来的优雅。

不要一棒子打死,异常是否可以反映业务流分支这正应该不用争论了。很多情况下调用者的范围或者调用后程序的行为是可以预知和限定的,程序是死的,人是活的,不要太绝对。

这里我只能说你们很无奈,已经找不到正确结果好的表示方法了,只能选择异常了。


何为好何为坏,能有效帮助调用者而不忽略所有可能的条件我看就是好,尽管异常对于大部分人看总像个“黑猫”。

我要是你的调用者我就很讨厌这样的设计,并认为你没帮助我什么反而增加了我很多麻烦,当然你可以说:咱们道不同不相为谋。

你可以讨厌这个设计,也可以忽略掉部分结果从而导致更大的错误,API设计者要求你处理你就要处理,比方说OSCache里getFromCache方法就会抛出NeedsRefreshException checked exception,强制你处理。
77 楼 carlkkx 2011-03-19  
我首先纠正你这世上没有几个GUI框架不是这样的,不仅仅是Swing,SWT ,WinForm如果你在事件分派线程中执行长时间任务都会卡住分派线程。
76 楼 pufan 2011-03-19  
carlkkx 写道
走本地调用和远程调用一回事的路线的人本根不知道时间也是接口的一部分。

如何把时间放在接口内,传递Date?
75 楼 pufan 2011-03-19  
carlkkx 写道
pufan 写道
carlkkx 写道
而且GUI程序,如果我点一下按钮,发现卡了半天,难道你这还不知道慢?而且不问青红皂白看到IOException就要构建后台线程,这本根就是增加复杂性,我们首先当然希望直接在EDT里面就能搞定,只有确实慢了我们才考虑后台线程。

如果你通过点按钮测试EDT问题的话,那看来你确实没开发过大型桌面程序。
本地测试环境和正式运行环境(很可能是公网)的网速完全不一样,往往本地不卡的程序上线就卡死。

如果和网络有通信的自然是会在后台线程,而且我给上层的通信API就有异步的,或者说使用异步本根就是常态。而且你不要用大型来掩盖你一个方法封装到最后居然连是否发生网络通信都已经搞不清了的问题。这说明你们的设计有问题,完全的过度封装,是不是要走本地调用和远程调用一回事的路线?结果封成这样还是不是一回事,你们浪费了封装人的苦心,因为你们还是通过IOException来分辨差别。


异步部分(或者大部分,我认为)情况下都不是常态,因为很可能需要堵塞在耗时操作线程后做其他耗时操作,作为api的设计者你不能假设所有调用方法情况都是异步,让调用者根据自己情况处理才是好的设计。

现实情况是:确实存在搞不清楚的状况,而且很频繁,这不是设计的问题,也不是过度封装,是Swing/Awt根本没有一个机制保障EDT安全,当然IO checked exception可以完美的解决这个问题。
74 楼 carlkkx 2011-03-19  
pufan 写道
carlkkx 写道
pufan 写道
carlkkx 写道
利用Checked Exception做业务流程分支设计比用返回值个人感觉更优雅
——————————————————————
晕倒,这已经是完全滥用异常了,程序执行的正常结果也用异常来表征了,如果我是调用者碰到这样的API我应该是难受死还哪来的优雅。

不要一棒子打死,异常是否可以反映业务流分支这正应该不用争论了。很多情况下调用者的范围或者调用后程序的行为是可以预知和限定的,程序是死的,人是活的,不要太绝对。

这里我只能说你们很无奈,已经找不到正确结果好的表示方法了,只能选择异常了。


何为好何为坏,能有效帮助调用者而不忽略所有可能的条件我看就是好,尽管异常对于大部分人看总像个“黑猫”。

我要是你的调用者我就很讨厌这样的设计,并认为你没帮助我什么反而增加了我很多麻烦,当然你可以说:咱们道不同不相为谋。
73 楼 carlkkx 2011-03-19  
走本地调用和远程调用一回事的路线的人本根不知道时间也是接口的一部分。
72 楼 pufan 2011-03-19  
carlkkx 写道
pufan 写道
carlkkx 写道
利用Checked Exception做业务流程分支设计比用返回值个人感觉更优雅
——————————————————————
晕倒,这已经是完全滥用异常了,程序执行的正常结果也用异常来表征了,如果我是调用者碰到这样的API我应该是难受死还哪来的优雅。

不要一棒子打死,异常是否可以反映业务流分支这正应该不用争论了。很多情况下调用者的范围或者调用后程序的行为是可以预知和限定的,程序是死的,人是活的,不要太绝对。

这里我只能说你们很无奈,已经找不到正确结果好的表示方法了,只能选择异常了。


何为好何为坏,能有效帮助调用者而不忽略所有可能的条件我看就是好,尽管异常对于大部分人看总像个“黑猫”。
71 楼 carlkkx 2011-03-19  
pufan 写道
carlkkx 写道
而且GUI程序,如果我点一下按钮,发现卡了半天,难道你这还不知道慢?而且不问青红皂白看到IOException就要构建后台线程,这本根就是增加复杂性,我们首先当然希望直接在EDT里面就能搞定,只有确实慢了我们才考虑后台线程。

如果你通过点按钮测试EDT问题的话,那看来你确实没开发过大型桌面程序。
本地测试环境和正式运行环境(很可能是公网)的网速完全不一样,往往本地不卡的程序上线就卡死。

如果和网络有通信的自然是会在后台线程,而且我给上层的通信API就有异步的,或者说使用异步本根就是常态。而且你不要用大型来掩盖你一个方法封装到最后居然连是否发生网络通信都已经搞不清了的问题。这说明你们的设计有问题,完全的过度封装,是不是要走本地调用和远程调用一回事的路线?结果封成这样还是不是一回事,你们浪费了封装人的苦心,因为你们还是通过IOException来分辨差别。
70 楼 carlkkx 2011-03-19  
pufan 写道
carlkkx 写道
利用Checked Exception做业务流程分支设计比用返回值个人感觉更优雅
——————————————————————
晕倒,这已经是完全滥用异常了,程序执行的正常结果也用异常来表征了,如果我是调用者碰到这样的API我应该是难受死还哪来的优雅。

不要一棒子打死,异常是否可以反映业务流分支这正应该不用争论了。很多情况下调用者的范围或者调用后程序的行为是可以预知和限定的,程序是死的,人是活的,不要太绝对。

这里我只能说你们很无奈,已经找不到正确结果好的表示方法了,只能选择异常了。
69 楼 pufan 2011-03-19  
carlkkx 写道
而且GUI程序,如果我点一下按钮,发现卡了半天,难道你这还不知道慢?而且不问青红皂白看到IOException就要构建后台线程,这本根就是增加复杂性,我们首先当然希望直接在EDT里面就能搞定,只有确实慢了我们才考虑后台线程。

如果你通过点按钮测试EDT问题的话,那看来你确实没开发过大型桌面程序。
本地测试环境和正式运行环境(很可能是公网)的网速完全不一样,往往本地不卡的程序上线就卡死。

相关推荐

    JavaReport-V3-Enterprise-Released.rar

    前几天要搞一个老掉牙的SSH项目,缺少了这个插件。全网去找,好不容易找到。放到WEB-INF/lib目录,发现不会自动引入,手动引入后,调用java report的程序不报错,但服务器出现放频繁出现it is not java class的错误...

    JAVA经典算法各种排序算法

    老掉牙 河內塔 費式數列 巴斯卡三角形 三色棋 老鼠走迷官(一) 老鼠走迷官(二) 騎士走棋盤 八個皇后 八枚銀幣 生命遊戲 字串核對 雙色、三色河內塔 背包問題(Knapsack Problem) 數、運算 蒙地...

    第二期:RIP高级,老掉牙的协议?其实没想象的那么简单.pptx

    RIP高级,老掉牙的协议?其实没想象的那么简单,资深华为讲师为你讲解rip协议

    JavaReport-V3-Enterprise-Released.jar

    前几天要搞一个老掉牙的SSH项目,缺少了这个插件。全网去找,好不容易找到。放到WEB-INF/lib目录,发现不会自动引入,手动引入后,调用java report的程序不报错,但服务器出现放频繁出现it is not java class的错误...

    pascal语言教程,老掉牙了,不过很不好找

    尽管它在现代编程中可能显得“老掉牙”,但Pascal在计算机科学教育领域曾扮演着重要的角色,对后来的编程语言如C、C++和Java产生了深远影响。这个“古董”教程可能对初学者或历史爱好者具有一定的价值。 Pascal的...

    老掉牙的lynx for win32

    尽管"老掉牙的lynx for win32"这个标题暗示这是一款较旧的版本,对于那些需要在Windows环境下运行命令行浏览器或者进行网页抓取、自动化任务的人来说,Lynx仍然是一个有用的工具。 Lynx的主要特点和优势在于: 1. *...

    C和JAVA经典算法.rar

    老掉牙 河內塔 費式數列 巴斯卡三角形 三色棋 老鼠走迷官(一) 老鼠走迷官(二) 騎士走棋盤 八個皇后 八枚銀幣 生命遊戲 字串核對 雙色、三色河內塔 背包問題(Knapsack Problem) 數、運算 蒙地...

    Java和C语言实现各种经典算法(含代码图例)

    老掉牙 河内塔 费式数列 巴斯卡三角形 三色棋 老鼠走迷官(一) 老鼠走迷官(二) 骑士走棋盘 八个皇后 八枚银币 生命游戏 字串核对 双色、三色河内塔 背包问题(Knapsack Problem) 数、运算 蒙地...

    c语言经典算法包括老掉牙,汉诺塔,三色旗

    老掉牙 河内塔 巴式数列 巴斯卡三角形 三色棋 老鼠走迷官(一) 老鼠走迷官(二) 骑士走棋盘 八个皇后 八枚银币 生命游戏 字串核对 双色、三色河内塔 背包问题(Knapsack Problem) 数、运算 蒙地卡罗法...

    一个老掉牙的故事作文.doc

    这篇文档实际上是一个关于亲情和爱情的故事,虽然标题和描述中没有明确的IT相关知识点,但从故事中我们可以引申出一些普遍的人生智慧和情感理解,这些也是人们在IT行业中经常需要处理的情感层面: 1. **习惯与依赖...

    老掉牙的问题:二叉树的遍历

    二叉树的三种遍历的递归和非递归方法,语言种类,C++,如果有不足的地方,请与作者联系,谢谢。

    SmaliInjector20170719

    dex2jar 的步骤使用的是 google 自家的 enjarify 工具,没使用老掉牙的、对部分混淆apk处理极不准确极不稳定的 dex2jar(d2j) 5). jar2dex 使用的是 android studio 自带的 dx.bat 工具,貌似 dex2jar(d2j) 在做jar...

    ACM经典算法 代码+详解

    老掉牙 河內塔 費式數列 巴斯卡三角形 三色棋 老鼠走迷官(一) 老鼠走迷官(二) 騎士走棋盤 八個皇后 八枚銀幣 生命遊戲 字串核對 雙色、三色河內塔 背包問題(Knapsack Problem) 數、運算 蒙地...

    Delphi Cmdshell 线程注入、文件释放程序

    内容索引:Delphi源码,系统相关,线程注入 这是个老掉牙的话题了,运行后AVP狂报,NOD32没反应,不过策略简直太牛了,主要实现了线程注入、文件释放、添加自启等一些常规手段来表现,作者是锦屏中学初二(10)班 王臻,...

    C语言经典算法大全.pdf

    老掉牙 河内塔 费式数列 巴斯卡三角形 三色棋 老鼠走迷官(一) 老鼠走迷官(二) 骑士走棋盘 八个皇后 八枚银币 生命游戏 字串核对 双色 三色河内塔 背包问题(Knapsack Problem) 数 运算 蒙地卡...

    LunchtimeBoredom:我在整个大三的午餐时间编写的代码。 常规编程问题和一些有趣的东西。 新项目即将推出新的存储库!

    随时为项目提出建议,解决同类问题很快就会老掉牙。 另外,这个神秘的“ GUI”是什么意思? 控制台文本是必经之路! 注意:maze.txt文件与SearchAlgorithms.java一起使用。 它只是一个示例文件,可以更改,但是...

    sdl推箱子源码和资源.zip_SDL游戏源码_sdl 游戏_sdl游戏_推箱子

    这个压缩包包含了一个基本的游戏实现,但描述中提到是“一个老掉牙的小小小游戏,只是半个成品”,意味着这可能是一个早期版本或未完成的项目。 在标签中,“sdl游戏源码”、“sdl_游戏”和“sdl游戏”都是与SDL...

    计算机组成实验

    不必再去实验室,用那些老掉牙的实验箱了。直接用它去做实验吧!

Global site tag (gtag.js) - Google Analytics