JDBC笔记-Transaction

来源:互联网 发布:数据分析项目案例 编辑:程序博客网 时间:2024/04/30 12:31

1.原子性 (Atomicity)

多个一系列的动作不可分割。

2. 一致性(Consistency)

强一致性:读操作可以立即读到提交的更新操作。
弱一致性:提交的更新操作,不一定立即会被读操作读到,此种情况会存在一个不一致窗口,指的是读操作可以读到最新值的一段时间。
最终一致性:是弱一致性的特例。事务更新一份数据,最终一致性保证在没有其他事务更新同样的值的话,最终所有的事务都会读到之前事务更新的最新值。如果没有错误发生,不一致窗口的大小依赖于:通信延迟,系统负载等。

3. 隔离性(Isolation)

并发访问时,事务的使用可能导致以下问题。
脏读:事务A修改了一个数据,但未提交,事务B读到了事务A未提交的更新结果,如果事务A提交失败,事务B读到的就是脏数据。
不可重复读:在同一个事务中,对于同一份数据读取到的结果不一致。比如,事务B在事务A提交前读到的结果,和提交后读到的结果可能不同。不可重复读出现的原因就是事务并发修改记录,要避免这种情况,最简单的方法就是对要修改的记录加锁,这会导致锁竞争加剧,影响性能。另一种方法是通过MVCC可以在无锁的情况下,避免不可重复读。
幻读:在同一个事务中,同一个查询多次返回的结果不一致。事务A新增了一条记录,事务B在事务A提交前后各执行了一次查询操作,发现后一次比前一次多了一条记录。幻读是由于并发事务增加记录导致的,这个不能像不可重复读通过记录加锁解决,因为对于新增的记录根本无法加锁。需要将事务串行化,才能避免幻读。

幻读和不可重复读的区别:不可重复读主要说的是修改,条件不变,两次读取的值不一样。
而幻读主要侧重于记录数,条件不变,两次读取的记录数不一样。

事务的隔离级别从低到高有:Mysql中默认的级别是Repeated Read。Oracle默认的是Read Committed。
Read Uncommitted:允许事务读取未被提交的变更,脏读,不可重复读和幻读的问题都会出现
Read Committed:只允许事务读取已经被其他事务提交的变更,可以避免脏读,但不可重复读和幻读问题仍然存在。
Repeated Read:确保事可以多次从一个字段中读取相同的值,在这个事务持续期间,禁止其他事务对这个字段进行更新,可以避免脏读和不可重复读,但是幻读的问题依然存在。
Serialization:事务串行化执行,隔离级别最高,牺牲了系统的并发性。可以解决并发事务的所有问题。通常,在工程实践中,为了性能的考虑会对隔离性进行折中。

4. 持久性(Durability)

事务提交后,对系统的影响是永久的。

5.事务编码举例

public class Transaction {public static void main(String[] args) throws Exception {Connection conn = DBTools.getConnection();conn.setAutoCommit(false);String send = "update user set balance = ? where username=?";PreparedStatement preparedStatement = conn.prepareStatement(send);try{preparedStatement.setObject(1, 50);preparedStatement.setObject(2, "tom");preparedStatement.executeUpdate();int i = 1/0; //出现异常回滚事务//RecievepreparedStatement.setObject(1, 150);preparedStatement.setObject(2, "lucy");preparedStatement.executeUpdate();conn.commit();}catch(Exception e){conn.rollback();e.printStackTrace();}finally{//所谓事务必须在同一个connection中处理,不同的连接不会相互约束//如果该连接需要做其他自动提交的事,可以调用conn.setAutoCommit(true);DBTools.release(null, preparedStatement, conn);}}}
<完>

0 0