RuntimeException和Exception事务处理中的区别

异常的分类:

① 异常的继承结构:基类为Throwable,Error和Exception继承Throwable,RuntimeException和IOException等继承Exception,具体的RuntimeException继承RuntimeException。

② Error和RuntimeException及其子类成为未检查异常(unchecked),其它异常成为已检查异常(checked)。

runtimeException就是运行时异常,它是java编译器事先不可预见的异常。

而其他的Exception异常大致的说是检查时异常,就是说帮你检查出来了可能出现的异常。此时你程序未执行,但是有可能抛出这个异常,所以提醒你记得捕获。

Exception体系包括RuntimeException体系和其他非RuntimeException的体系

① RuntimeException:RuntimeException体系包括错误的类型转换、数组越界访问和试图访问空指针等等。处理RuntimeException的原则是:如果出现RuntimeException,那么一定是程序员的错误。例如,可以通过检查数组下标和数组边界来避免数组越界访问异常。

②其他非RuntimeException(IOException等等):这类异常一般是外部错误,例如试图从文件尾后读取数据等,这并不是程序本身的错误,而是在应用环境中出现的外部错误。

1、为什么要声明方法抛出异常?

方法是否抛出异常与方法返回值的类型一样重要。假设方法抛出异常却没有声明该方法将抛出异常,那么客户程序员可以调用这个方法而且不用编写处理异常的代码。那么,一旦出现异常,那么这个异常就没有合适的异常控制器来解决。

2、为什么抛出的异常一定是已检查异常?

RuntimeException与Error可以在任何代码中产生,它们不需要由程序员显示的抛出,一旦出现错误,那么相应的异常会被自动抛出。而已检查异常是由程序员抛出的,这分为两种情况:客户程序员调用会抛出异常的库函数(库函数的异常由库程序员抛出);客户程序员自己使用throw语句抛出异常。遇到Error,程序员一般是无能为力的;遇到RuntimeException,那么一定是程序存在逻辑错误,要对程序进行修改(相当于调试的一种方法);只有已检查异常才是程序员所关心的,程序应该且仅应该抛出或处理已检查异常。

注意:覆盖父类某方法的子类方法不能抛出比父类方法更多的异常,所以,有时设计父类的方法时会声明抛出异常,但实际的实现方法的代码却并不抛出异常,这样做的目的就是为了方便子类方法覆盖父类方法时可以抛出异常。

使用spring难免要用到spring的事务管理,要用事务管理又会很自然的选择声明式的事务管理,在spring的文档中说道,spring声明式事务管理默认对非检查型异常和运行时异常进行事务回滚,而对检查型异常则不进行回滚操作。

那么什么是检查型异常什么又是非检查型异常呢?

最简单的判断点有两个:

1.继承自runtimeexception或error的是非检查型异常,而继承自exception的则是检查型异常(当然,runtimeexception本身也是exception的子类)。

2.对非检查型类异常可以不用捕获,而检查型异常则必须用try语句块进行处理或者把异常交给上级方法处理总之就是必须写代码处理它。所以必须在service捕获异常,然后再次抛出,这样事务方才起效。

Spring默认情况下会对运行期例外(RunTimeException)进行事务回滚。这个例外是unchecked

如果遇到checked意外就不回滚。

如何改变默认规则:

1 让checked例外也回滚:在整个方法前加上 @Transactional(rollbackFor=Exception.class)

2 让unchecked例外不回滚: @Transactional(notRollbackFor=RunTimeException.class)

3 不需要事务管理的(只查询的)方法:@Transactional(propagation=Propagation.NOT_SUPPORTED)

在整个方法运行前就不会开启事务还可以加上:@Transactional(propagation=Propagation.NOT_SUPPORTED,readOnly=true),这样就做成一个只读事务,可以提高效率。

import javax.annotation.Resource;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import com.dao.CompanyDao;
import com.entry.TCompanyInfo;
@Service("companyService")
@Transactional
public class CompanyService {

 @Resource(name="companyDao")
 private CompanyDao companyDao;
 public void setCompanyDao(CompanyDao companyDao) {
  this.companyDao = companyDao;
 }
 public CompanyDao getCompanyDao() {
  return companyDao;
 }

 @Transactional(readOnly=false,propagation=Propagation.REQUIRED,rollbackFor={Exception.class})//readOnly=true慎用(不可写事务)
 public void test(TCompanyInfo tc){
  try{

   companyDao.createObj(tc);
   String s=null;
   s.length();  //假设会抛出NullPointerException,就会执行catch里的,如果不在catch里throw一个
                           RuntimeException子类,依然不会rollback
  }
  catch(Exception e){
   //throw new Exception("runtimeException");
   System.out.println("exception");
   throw new NumberFormatException("format exception"); //重抛一个Exception,才能rollback
  }
 }

}

在Spring里,同样只会rollback unchecked exception(RuntimeExcption及子类),而checked exception(Exception及子类)是不会rollback的,除非你特别声明。

   @Transactional(readOnly = false, propagation = Propagation.REQUIRES_NEW,rollbackFor = {MyException1.class,MyException2.class})

因此所有在service层方法中用throws定义的Exception,都必须在事务定义中进行rollback设定。(请勿善忘)

所有在service层方法中被catch处理了的异常,又希望容器辅助rollback的话,必须重抛一个预定义的RuntimeException的子类。(请勿回望)

参考文章:http://zw7534313.iteye.com/blog/691398

RuntimeException和Exception事务处理中的区别

时间: 2024-10-07 21:12:20

RuntimeException和Exception事务处理中的区别的相关文章

Java Exception和Error的区别

Java中异常的抽象类是Throwable,在此基础上,派生出两大类:Error和Exception. Error是程序中的严重错误,不应该用try-catch包括.Javadoc的说明如下: An Error is a subclass of Throwable that indicates serious problems that a reasonable application should not try to catch. Most such errors are abnormal

RuntimeException和Exception的区别

1.java将所有的错误封装为一个对象,其根本父类为Throwable, Throwable有两个子类:Error和Exception. 2.Error是Throwable 的子类,用于指示合理的应用程序不应该试图捕获的严重问题.大多数这样的错误都是异常条件.虽然   ThreadDeath 错误是一个“正规”的条件,但它也是 Error 的子类,因为大多数应用程序都不应该试图捕获它.在执行该方法期间,无需在其 throws 子句中声明可能抛出但是未能捕获的 Error的任何子类,因为这些错误可

RuntimeException和Exception区别

1.java将所有的错误封装为一个对象,其根本父类为Throwable, Throwable有两个子类:Error和Exception. 2.Error是Throwable 的子类,用于指示合理的应用程序不应该试图捕获的严重问题.大多数这样的错误都是异常条件.虽然   ThreadDeath 错误是一个“正规”的条件,但它也是 Error 的子类,因为大多数应用程序都不应该试图捕获它.在执行该方法期间,无需在其 throws 子句中声明可能抛出但是未能捕获的 Error的任何子类,因为这些错误可

Java中RuntimeException和Exception

在java的异常类体系中,Error和RuntimeException是非检查型异常,其他的都是检查型异常. 所有方法都可以在不声明throws的情况下抛出RuntimeException及其子类 不可以在不声明的情况下抛出非RuntimeException 简单的说,非RuntimeException必要自己写catch块处理掉.   RuntimeException不用try catch捕捉将会导致程序运行中断,若用则不会中断 1.RuntimeException 今天摩根IT电面的时候被问

在spring+hibernaet+mysql事务处理中遇到的一些坑

spring的事务处理本来就是依赖于底层的实现,比如hibernate及数据库本身. 所以,当使用mysql数据库时,首先要确定的是,所操作的对象表是innodb格式的. 1. read-only方法中进行更新或插入操作时,并不总报错 在service层的方法中定义了事务,并且在spring配置文件中定义了如下的传播方式: <tx:attributes > <tx:method name="save*" propagation="REQUIRED"

异常:exception和error的区别

Throwable 是所有 Java 程序中错误处理的父类 ,有两种子类: Error 和 Exception . Error :表示由 JVM 所侦测到的无法预期的错误,由于这是属于 JVM 层次的严重错误 ,导致 JVM 无法继续执行,因此,这是不可捕捉到的,无法采取任何恢复的操作,顶多只能显示错误信息. Exception :表示可恢复的例外,这是可捕捉到的. Java 提供了两类主要的异常 :runtime exception 和 checked exception . checked

JD订单去重的问题:谈分布式事务处理中领域驱动设计的原则

原始文章:http://www.csdn.net/article/2015-01-15/2823577 订单号去重的问题:假设A节点向B节点发送新订单请求,但是网络有可能失败,则这个分布式事务有可能出现B节点上已经成功执行,但是A却以为失败了,导致重新发送订单请求,造成重复的订单 要点:关键问题是订单号这一ID信息要防止重复生成,如果ID号能够提前生成的话,就可以在每次发送这一ID信息,使得请求的每次处理做到幂等. 因此,JD现在的方案相当于在B节点上根据商品信息.客户信息等等,做了一个到订单I

Exception 和 Error 有什么区别么

声明 本篇所涉及的提问,正文的知识点,全都来自于杨晓峰的<Java核心技术36讲>,当然,我并不会全文照搬过来,毕竟这是付费的课程,应该会涉及到侵权之类的问题. 所以,本篇正文中的知识点,是我从课程中将知识点消耗后,用个人的理解.观念所表达出来的文字,参考了原文,但由于是个人理解,因此不保证观点完全正确,也不代表错误的观点是课程所表达的.如果这样仍旧还是侵权了,请告知,会将发表的文章删掉. 当然,如果你对此课程有兴趣,建议你自己也购买一下,新用户立减 30,微信扫码订阅时还可以返现 6 元,相

Throwable和Exception的区别

Java语言要求java程序中(无论是谁写的代码)所有抛出(throw)的异常都必须是从Throwable派生而来.当然,实际的Java编程中,由于JDK平台已经为我们设计好了非常丰富和完整的异常对象分类模型.因此,java程序员一般是不需要再重新定义自己的异常对象.而且即便是需要扩展自定义的异常对象,也往往会从Exception派生而来.所以,对于java程序员而言,它一般只需要在它的顶级函数中catch(Exception ex)就可以捕获出所有的异常对象. 所有异常对象的根基类是 Thro