JDBC的事务

事务的概念:

 数据库中一些操作的集合通常是一个独立单元,而事务就是构成单一逻辑工作单位的操作集合。

    已提交事务是指成功执行完毕的事务,未能成功完成的事务称为中止事务,对中止事务造成的变更需要进行撤销处理,称为事务回滚。

 

事务的特性:

事务具有ACID4个特性。

 

    1.原子性(Atomicity)

    事务中的全部操作在数据库中是不可分割的,要么全部完成,要么均不执行。

 

    2.一致性(Consistency)

    几个并行执行的事务,其执行结果必须与按某一顺序串行执行的结果相一致。

 

    3.隔离性(Isolation)

    事务的执行不受其他事务的干扰,事务执行的中间结果对其他事务必须是透明的。

 

    4.持久性(Durability)

    对于任意已提交事务,系统必须保证该事务对数据库的改变不被丢失,即使数据库出现故障。

JDBC事务:

1.         public interface Connection:

与特定数据库的连接(会话)。在连接上下文中执行 SQL 语句并返回结果。

Connection 对象的数据库能够提供信息描述其表、所支持的 SQL 语法、存储过程和此连接的功能等。此信息是使用 getMetaData 方法获得的。

注:默认情况下,Connection 对象处于自动提交模式下,这意味着它在执行每个语句后都会自动提交更改。如果禁用自动提交模式,为了提交更改,必须显式调用 commit 方法;否则无法保存数据库更改。

2.     JDBC事务的概念:

 

在jdbc的数据库操作中,一项事务是由一条或是多条表达式所组成的一个不可分割的工作单元。我们通过提交commit()或是回滚rollback()来结束事务的操作。关于事务操作的方法都位于接口java.sql.Connection中。

2.  特点:

★ 在jdbc中,事务操作缺省是自动提交。也就是说,一条对数据库的更新表达式代表一项事务操作,操作成功后,系统将自动调用commit()来提交,否则将调用rollback()来回滚。

★ 在jdbc中,可以通过调用setAutoCommit(false)来禁止自动提交。之后就可以把多个数据库操作的表达式作为一个事务,在操作完成后调用commit()来进行整体提交,倘若其中一个表达式操作失败,都不会执行到commit(),并且将产生响应的异常;此时就可以在异常捕获时调用rollback()进行回滚。这样做可以保持多次更新操作后,相关数据的一致性,示例如下:

    try {

        conn = DriverManager.getConnection  ; 

        conn.setAutoCommit(false);//禁止自动提交,设置回滚点

        stmt = conn.createStatement();

        stmt.executeUpdate(“alter table …”); //数据库更新操作1

        stmt.executeUpdate(“insert into table …”)&#59; //数据库更新操作2

        conn.commit()&#59; //事务提交

     }catch(Exception ex) {    

         ex.printStackTrace();

         try {

          conn.rollback()&#59; //操作不成功则回滚

          }catch(Exception e) {

         e.printStackTrace();

           }

}

★      jdbc API支持事务对数据库的加锁,并且提供了5种操作支持,2种加锁密度。

 

5种支持:

static int TRANSACTION_NONE                = 0; //禁止事务操作和加锁。

static  int TRANSACTION_READ_UNCOMMITTED    = 1; //允许脏数据读写(dirty reads)、重复读写(repeatable reads)和影象读写(phntom reads)

static  int TRANSACTION_READ_COMMITTED      = 2;//禁止脏数据读写(dirty reads),允许重复读写(repeatable reads)和影象读写(phntom reads)

static  int TRANSACTION_REPEATABLE_READ     = 4;//禁止脏数据读写(dirty reads)和重复读写(repeatable reads),允许影象读写(phntom reads)

static  int TRANSACTION_SERIALIZABLE        = 8;//禁止脏数据读写(dirty reads)、重复读写(repeatable reads)和允许影象读写(phntom reads)

2种密度:

最后一项为表加锁,其余3~4项为行加锁。 

      脏数据读写(dirty reads):当一个事务修改了某一数据行的值而未提交时,另一事务读取了此行值。倘若前一事务发生了回滚,则后一事务将得到一个无效的值(脏数据)。

      重复读写(repeatable reads):当一个事务在读取某一数据行时,另一事务同时在修改此数据行。则前一事务在重复读取此行时将得到一个不一致的值。

      影象读写(phantomreads):当一个事务在某一表中进行数据查询时,另一事务恰好插入了满足了查询条件的数据行。则前一事务在重复读取满足条件的值时,将得到一个额外的“影象“值。

     Jdbc根据数据库提供的缺省值来设置事务支持及其加锁,当然,也可以手工设置:

            setTransactionIsolation(TRANSACTION_READ_UNCOMMITTED);

    可以查看数据库的当前设置:

            getTransactionIsolation()

需要注意的是,在进行受动设置时,数据库及其驱动程序必须得支持相应的事务操作操作才行。

       上述设置随着值的增加,其事务的独立性增加,更能有效的防止事务操作之间的冲突;同时也增加了加锁的开销,降低了用户之间访问数据库的并发性,程序的运行效率也回随之降低。因此得平衡程序运行效率和数据一致性之间的冲突。一般来说,对于只涉及到数据库的查询操作时,可以采用TRANSACTION_READ_UNCOMMITTED方式;对于数据查询远多于更新的操作,可以采用TRANSACTION_READ_COMMITTED方式;对于更新操作较多的,可以采用TRANSACTION_REPEATABLE_READ;在数据一致性要求更高的场合再考虑最后一项,由于涉及到表加锁,因此会对程序运行效率产生较大的影响。

另外,在oracle中数据库驱动对事务处理的缺省值是TRANSACTION_NONE,即不支持事务操作,所以需要在程序中手动进行设置。

3.  小结

jdbc提供的对数据库事务操作的支持是比较完整的,通过事务操作可以提高程序的运行效率,保持数据的一致性 

 

阅读更多
个人分类: JAVAEE
想对作者说点什么? 我来说一句

没有更多推荐了,返回首页

加入CSDN,享受更精准的内容推荐,与500万程序员共同成长!
关闭
关闭