`
qys2010
  • 浏览: 127364 次
  • 性别: Icon_minigender_1
  • 来自: 上海
社区版块
存档分类
最新评论

java的checked exception和unchecked exception

    博客分类:
  • java
阅读更多
异常的概念 
       任何的异常都是Throwable类,并且在它之下包含两个子类Error / Exception,而Error仅在当在Java虚拟机中发生动态连接失败或其它的定位失败的时候,Java虚拟机抛出一个Error对象。典型的程序不捕获或抛出Errors对象,你可能永远不会遇到需要实例化Error的应用,那就让我们关心一下Exception。

       Exception中比较重要的就是RuntimeException(运行时异常)-可能在执行方法期间抛出但未被捕获的 RuntimeException 的任何子类都无需在 throws 子句中进行声明,也就是说你的应用应该不去“关心”(说不关心是不服责任的,但只是你不应该试图实例化它的字类)。  RuntimeException,就如同你不应该关心Error的产生与处理一样!RuntimeException描述的是程序的错误引起来的,因该由程序负担这个责任!(从责任这个角度看Error属于JVM需要负担的责任;RuntimeException是程序应该负担的责任;checked exception 是具体应用负担的责任)

       除了Error与RuntimeException,其他剩下的异常都是你需要关心的,而这些异常类统称为Checked Exception,至于Error与RuntimeException则被统称为Unchecked Exception.



         关于 Java 中引入的 Checked Exceptions,目前存在着很多反对意见。正方的观点是引入 Checked Exceptions,可以增加程度的鲁棒性。反方的观点是 Checked Exceptions 很少被开发人员正确使用过,并且降低了程序开发的生产率和代码的执行效率。


Java 中定义了两类异常:

1) Checked exception: 这类异常都是Exception的子类 。异常的向上抛出机制进行处理,如果子类可能产生A异常,那么在父类中也必须throws A异常。可能导致的问题:代码效率低,耦合度过高。C#中就没有使用这种异常机制。

2) Unchecked exception: 这类异常都是RuntimeException的子类,虽然RuntimeException同样也是Exception的子类,但是它们是特殊的,它们不能通过client code来试图解决,所以称为Unchecked exception 。 

  

(JAVA视线论坛robbin's view,个人觉得用来做业务流程控制违背了Exception设计的初衷,但可以借鉴一下)

     在使用UseCase来描述一个场景的时候,有一个主事件流和n个异常流。异常流可能发生在主事件流的过程,而try语句里面实现的是主事件流,而catch里面实现的是异常流,在这里Exception不代表程序出现了异常或者错误,Exception只是面向对象化的业务逻辑控制方法。如果没有明白这一点,那么我认为并没有真正明白应该怎么使用Java来正确的编程。
      而我自己写的程序,会自定义大量的Exception类,所有这些Exception类都不意味着程序出现了异常或者错误,只是代表非主事件流的发生的,用来进行那些分支流程的流程控制的。例如你往权限系统中增加一个用户,应该定义1个异常类,UserExistedException,抛出这个异常不代表你插入动作失败,只说明你碰到一个分支流程,留待后面的catch中来处理这个分支流程。传统的程序员会写一个if else来处理,而一个合格的OOP程序员应该有意识的使用try catch 方式来区分主事件流和n个分支流程的处理,通过try catch,而不是if else来从代码上把不同的事件流隔离开来进行分别的代码撰写。


(另外一种观点,不同于robbin,个人赞同,并引用于此)

1。什么时候抛出异常--涉及到服务类
2。抛出checked还是unchecked的异常--涉及到客户类

       对第一个问题来说,我想异常本身这个字解释了某些东西,异常就是我们认为在正常情况下不可能发生的问题,并且服务代码不知道如何去处理。譬如说我做一个监控程序,需要用压缩卡提供的API去初始化所有的板卡,API提供的是boolean型的返回值,但我把这个API变成抛出一个异常,因为除非特殊原因,我不认为会发生初始化失败的情况,当然更不知道怎样去处理这个问题。又譬如Hibernate里面的LoadObject使用没有发现这个对象存在,那Hibernate也是认为不可能的,除非其他代码直接删除了数据库里面的记录,那么也需要抛出异常。当然Hibernate本身也不知道如何处理这种情况。
       但是如果发生的情况是可以预期的,那我不认为应该抛出例外。象上面这个userExist的情况,我认为应该在前面已经分流,应该首先判断这个用户是否存在,if(userExists()),然后进行处理,而不应当抛出例外。以及login应当返回true或者false。也就是说,这些属于程序的正常流程,而不是例外,不是异常。把例外作为正常程序流程的控制机制,只不过是把服务代码中的if转移到客户代码去,没有减少任何需要处理的代码,反而增加了系统的负担(生成例外栈)。
       还有抛出异常的情况是违反方法的先决条件,每一个方法都有自己的先决条件和后置条件,方法只有在正确的前提下才能执行达到一个正确的后果,(所谓类的不变量)。譬如你去存取一个数组的某一个元素,这个存取方法有一个前提条件,就是你的索引应当落入它的最大下标和最小下标之间,不然就应当抛出一个例外。

         对于第二个问题,端视于客户代码是否能够根据这个例外进行合理的处理。如果客户代码根本就不知道如何处理这个例外,应当把它作为一个unchecked例外,例如上面下标的问题,客户代码用一个不合法的下标来存取数组,那么抛出一个checked例外以后,客户代码是+1还是-1?显然根本就不可能做出“合理的”处理,客户既然不能处理,还要强制它去处理,那么就是捕获,打印了事,没有增加任何价值。但是如果是客户可以处理的,或者可以选择不同的方式处理的,那么就可能需要用checked,但我发现很少有这样的情况。对于类似于RemoteException或者SQLException这些Exception,我一般都转换为具体的业务Exception,而我所有的业务Exception都是RuntimeException.

         所以我的观点是,是否抛出例外就是服务代码是否进行合理的处理,抛出什么类型的例外就是客户代码是否能够合理的处理。


保护封装性的代码实例:

      不要让你要抛出的checked exception升级到较高的层次。例如,不要让SQLException延伸到业务层。业务层并不需要(不关心?)SQLException。你有两种方法来解决这种问题:

1)转变SQLException为另外一个checked exception,如果客户端并不需要恢复这种异常的话;
2)转变SQLException为一个unchecked exception,如果客户端对这种异常无能为力的话;

      多数情况下,客户端代码都是对SQLException无能为力的,因此你要毫不犹豫的把它转变为一个unchecked exception,看看下边的代码:

public void dataAccessCode(){
try{
      .  .some code that throws SQLException
}catch(SQLException ex){
     ex.printStacktrace();
}
}

       上边的catch块紧紧打印异常信息而没有任何的直接操作,这是情有可原的,因为对于SQLException你还奢望客户端做些什么呢?(但是显然这种就象什么事情都没发生一样的做法是不可取的)那么有没有另外一种更加可行的方法呢? 看下面代码:
public void dataAccessCode(){
    try{
          ..some code that throws SQLException
      }catch(SQLException ex){
         throw new RuntimeException(ex);
   }
}
     上边的做法是把SQLException转换为RuntimeException,一旦SQLException被抛出,那么程序将抛出RuntimeException,此时程序被挂起并返回客户端异常信息。 调用该方法的程序代码中也不用再捕获SQLException异常:

public void do(){

     dataAccessCode();   
}



本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/zhiweiv/archive/2008/12/01/3419952.aspx
分享到:
评论

相关推荐

    Checked and Unchecked Exception

    异常分为两种类型:已检查异常(Checked Exception)和未检查异常(Unchecked Exception)。 **已检查异常(Checked Exception)** 已检查异常是那些在编译时需要处理的异常。Java强制程序员要么在方法签名中声明...

    详解Java中的checked异常和unchecked异常区别

    Java中的checked异常和unchecked异常区别详解 Java中的checked异常和unchecked异常是Java语言中两种不同的异常类型,它们之间的区别是很多开发者容易混淆的。下面,我们将详细介绍checked异常和unchecked异常的概念...

    通过实例了解java checked和unchecked异常

    通过实例了解 Java checked 和 unchecked 异常 Java 异常分为两种类型:checked 异常和 unchecked 异常。checked 异常是可以在执行过程中恢复的,例如无效的用户输入、文件不存在、网络或者数据库链接错误等。这些...

    Java throw Exception实现异常转换

    Java throw Exception实现异常转换是Java语言中的一种异常处理机制,它允许开发者将 checked exception 转换为 unchecked exception,从而使得异常处理变得更加灵活和便捷。本文将详细介绍Java throw Exception实现...

    Java的checked和unchecked异常

    Java异常分为两种类型,checked异常和unchecked异常,另一种叫法是异常和错误。  简单地讲,checked是可以在执行过程中恢复的,而unchecked异常则是无法处理的错误。  checked异常:  表示无效,不是程序中...

    Java中Error与Exception的区别.doc

    在 Java 中,定义了两类异常:Checked exception 和 Unchecked exception。 Checked exception 是 Exception 的子类,它们的异常向上抛出机制进行处理。例如,如果子类可能产生 A 异常,那么在父类中也必须 throws ...

    Java常见工具类及异常处理

    在本文中,我们将详细介绍 Java 异常处理机制,包括 try、catch、finally 块、throws、throw 关键字、Exception 和 Error 类、Checked Exception 和 Unchecked Exception 等概念,并提供了多种异常处理的示例代码,...

    JAVA Exception Handling & UI Design

    Java中的异常分为两种类型:Checked异常和Unchecked异常。Checked异常是那些在编译时期就需要被处理的异常,比如FileNotFoundException。在编写代码时,如果可能会抛出这些异常,那么必须使用try-catch语句块来捕获...

    java 面试常见问题整理

    Checked Exception 和 Unchecked Exception 有什么区别? Throwable 类常用方法有哪些? try-catch-finally 如何使用? finally 中的代码一定会执行吗? 如何使用 try-with-resources 代替try-catch-finally? I/O ...

    Java语言程序设计基础篇课后题答案-Chapter17ExceptionsandAssertions.pdf

    本资源对Java语言程序设计基础篇的Chapter 17 Exceptions and Assertions进行了详细的解释和知识点总结,涵盖了Java异常类的继承结构、claiming exceptions、checked exception和unchecked exception、throw语句和...

    Java常见基础知识总结

    Exception又可以分为Checked Exception(受检查异常)和Unchecked Exception(不受检查异常)。Checked Exception即受检查异常,Java代码在编译过程中,如果受检查异常没有被catch或者throws关键字处理的话,就没...

    java异常(Exception)处理机制详解

    Exception 又分为两类:CheckedException 和 UncheckedException。 CheckedException 需要用 try...catch... 显示的捕获,而 UncheckedException 不需要捕获。 三、 异常的使用 异常的使用可以分为两类:Checked...

    基于JAVA语言的异常处理探讨分析 (1).pdf

    JAVA语言的异常可以分为两大类:Checked Exception和Unchecked Exception。Checked Exception是编译器强制捕获的异常,而Unchecked Exception是运行时抛出的异常。常见的Checked Exception包括IOException、...

    java中Exception的细节

    Exception类是Java中异常处理的核心,它位于`java.lang`包中,是所有检查型异常(checked exceptions)和非检查型异常(unchecked exceptions)的基类。本文将深入探讨Java中的Exception细节。 首先,异常分为两种...

    Java异常处理机制及其在项目中的应用.pdf

    Java 异常处理机制可以分为两大类:Checked Exception 和 Unchecked Exception。Checked Exception 是在编译期检查的异常,而 Unchecked Exception 是在运行期检查的异常。 在 Java 中,异常对象都是继承自 ...

    Java面向对象及异常_附件.pdf

    Java中的异常可以分为两类:Checked Exception和Unchecked Exception。Checked Exception是指编译器可以检查的异常,如IOException、SQLException等。Unchecked Exception是指编译器不能检查的异常,如...

    Java的内置异常-Java教程共1页.pdf.zip

    Unchecked Exception是所有继承自`java.lang.RuntimeException`的类,包括`java.lang.NullPointerException`和`java.lang.ArithmeticException`等。这些异常在编译时不强制要求处理,但在运行时如果抛出,程序会终止...

    浅谈Java异常.docx

    通过合理地划分`CheckedException`和`UncheckedException`,我们可以更好地管理程序的异常情况,提高代码的健壮性和可读性。在实际编程中,应该根据异常的性质和预期的处理方式来选择合适的异常类型,从而确保程序在...

Global site tag (gtag.js) - Google Analytics