数据库事务

2012/04/08 1791点热度 0人点赞 0条评论

数据库事务(Database Transaction) ,是指作为单个逻辑工作单元执行的一系列操作。 事务处理可以确保除非事务性单元内的所有操作都成功完成,否则不会永久更新面向数据的资源。通过将一组相关操作组合为一个要么全部成功要么全部失败的单元,可以简化错误恢复并使应用程序更加可靠。一个逻辑工作单元要成为事务,必须满足所谓的ACID(原子性、一致性、隔离性和持久性)属性。

事务:是指一组逻辑操作单元,使数据从一种状态换到另一个状态

事务的四个属性

   1,原子性(atomicity)

          不可分割,要么都发生,要么不发生

    2,一致性(consistency)

         从一个一致性状态变换到另外一个一致性状态

  3,隔离性(isolation)

         一个事物的执行不能被其他事务干扰

   4,持久性(durability)

        事务一旦提交,对数据库中的数据的改变就是永久的

案例:

private Connection conn = null;  
private Statement st = null;  
try {  
    conn=DriverManager.getConnection(url, name, password);
    st=conn.createStatement(); 
    conn.setAutoCommit(false);  //将自动提交设置为false   
                                                        
    st.executeUpdate("修改SQL"); //执行修改操作  
    st.executeQuery("删除SQL");  //执行删除操作                 
    conn.commit();      //当两个操作成功后手动提交  
                                                            
} catch (Exception e) {  
    conn.rollback();    //一旦其中一个操作出错都将回滚,使两个操作都不成功  
    e.printStackTrace();  
}

跨数据库的事务提交

      JTA

事务并发处理可能引起的问题

     脏读(dirty read) 一个事务读取了另一个事务尚未提交的数据,
     不可重复读(non-repeatable read) 一个事务的操作导致另一个事务前后两次读取到不同的数据
     幻读(phantom read) 一个事务的操作导致另一个事务前后两次查询的结果数据量不同。

举例:
    事务A、B并发执行时,
       当A事务update后,B事务select读取到A尚未提交的数据,此时A事务rollback,则B读到的数据是无效的"脏"数据。
       当B事务select读取数据后,A事务update操作更改B事务select到的数据,此时B事务再次读去该数据,发现前后两次的数据不一样。
      当B事务select读取数据后,A事务insert或delete了一条满足A事务的select条件的记录,此时B事务再次select,发现查询到前次不存在的记录("幻影"),或者前次的某个记录不见了。

JDBC对事务的支持体现在三个方面:

   一, 自动提交模式(Auto-commit mode)
       Connection提供了一个auto-commit的属性来指定事务何时结束。
        a).当auto-commit为true时,当每个独立SQL操作的执行完毕,事务立即自动提交,也就是说每个SQL操作都是一个事务。一个独立SQL操作什么时候算执行完毕,JDBC规范是这样规定的:

       对数据操作语言(DML,如insert,update,delete)和数据定义语言(如create,drop),语句一执行完就视为执行完毕。

       对select语句,当与它关联的ResultSet对象关闭时,视为执行完毕。
       对存储过程或其他返回多个结果的语句,当与它关联的所有ResultSet对象全部关闭,所有update count(update,delete等语句操作影响的行数)和output parameter(存储过程的输出参数)都已经获取之后,视为执行完毕。
      b). 当auto-commit为false时,每个事务都必须显示调用commit方法进行提交,或者显示调用rollback方法进行回滚。auto-commit默认为true。

  二, 事务隔离级别(transaction isolation levels)

      1,串行化(serializable)  禁止脏读、不可重复读和幻读。

      2,可重复读(repeatable read)   禁止脏读和不可重复读,单运行幻读。

      3,读已提交(read committed)禁止脏读,但允许不可重复读和幻读。

      4,读未提交(read uncommitted)允许脏读、不可重复读和幻读。

     sqlserver默认为 read committed

     mysql 默认为 repeatable read

     oracle 只支持read committed 和serializable,默认为 read committed    

   select @@tx_isolation;

      mysql中 查看数据库的默认隔离级别

    更改隔离界别

        set transaction isolation level read uncommitted  设置当前窗口的隔离级别

        set global transaction  设置全局的隔离级别

        select @@autocommit  查看事务的提交方式

        set tutocommit=0;  设置事务的提交方式

      mysql中的事务处理方式: begin,rollback,commit

 三.保存点(SavePoint)
     JDBC定义了SavePoint接口,提供在一个更细粒度的事务控制机制。当设置了一个保存点后,可以rollback到该保存点处的状态,而不是rollback整个事务。
      Connection接口的setSavepoint和releaseSavepoint方法可以设置和释放保存点。

    JDBC规范虽然定义了事务的以上支持行为,但是各个JDBC驱动,数据库厂商对事务的支持程度可能各不相同。如果在程序中任意设置,可能得不到想要的效果。为此,JDBC提供了   DatabaseMetaData接口,提供了一系列JDBC特性支持情况的获取方法。比如,通过DatabaseMetaData.supportsTransactionIsolationLevel方法可以判断对事务隔离级别的支持情况,通过DatabaseMetaData.supportsSavepoints方法可以判断对保存点的支持情况。

yxkong

这个人很懒,什么都没留下

文章评论