事务隔离级别

事务的 ACID 属性之一是隔离性。隔离允许事务行为(无论是读还是写数据)独立或隔离于其他并发运行的事务。通过控制隔离,每个事务在其行动时间里都像是修改数据库的惟一事务。一个事务与其他事务隔离的程度称为隔离级别。

锁机制和同步用来控制隔离级别。随着隔离级别增加,需要更多的锁和同步。由于锁控制数据资源,其他尝试执行任何数据操作的事务必须等待,直到锁被释放。因此,增加隔离级别将以性能为代价。相反,随者隔离级别降低,因事务耗费较少的时间来等待锁被释放,将提高性能。

数据一致性

对事务设置隔离级别来处理下列数据一致性问题:

 

  • 脏数据读(Dirty read)
  • 不可重复读(Unrepeatable read)
  • 影像读(Phantom read)

脏数据读

当从数据库读取未经提交的数据时,发生脏数据读。读取的数据没有与数据库里的真实数据同步。

考虑下面的场景,其中两个事务在读取和更新数据库的 String 字段 X。String X 的初始值是 foo:

1.事务 1 读取 String X 的值 foo。
2.事务 1 将 String X 的当前值与 bar 连接并将其保存到数据库中。
3.X 的新值是 foobar。事务 1 还没有发出提交语句。
4.事务 2 读取 String X 的值,即 foobar。
5.事务 1 中止。
6.事务 2 将 String X 与 bar 连接并将其保存至数据库。
7.X 的新值是 foobarbar,这时其正确的值应该是 foobar。
8.事务 2 对 String X 的值执行了脏数据读。
这里的问题是一个事务可以改变值,而另一个事务可能在初始修改被提交前读取其值。数据是脏的,并不能表示数据的真实状态。

不可重复读

如果应用程序从数据库读取数据,然后又重读已经被修改的数据(可能以后在同一事务中),那么会发生不可重复读。考虑下面的场景,其中两个应用程序在读取和更新同一数据:

1.应用程序 1 读取 String X 的值 foo。
2.应用程序 2 更新 String X 的值为 foobar。
3.应用程序 1 重读 String 的值并发现其已改为 foobar。
因此在读取之间,数据的值已改变并变得不一致。

影像读

影像读 与不可重复读类似。但是,影像读会将新数据插入到数据库中。应用程序从数据库中读取数据集,然后确定在其重读同一数据集时,附加的数据已经被添加。考虑下面的场景,其中两个应用程序在读取和更新数据库的同一数据:

1.应用程序 1 搜索符合某个条件的数据并返回五行的数据集。
2.应用程序 2 将五个满足应用程序 1 的搜索条件的附加行添加到数据库。
3.在应用程序 1 基于其初始条件重读数据库(且期望得到五行)时,将返回 10 行。
同样,在读取之间数据变得不一致。

选择隔离级别

隔离的四个级别列在下面,按最低(最弱)隔离级别到最高(最强)级别的顺序排列。记住当提高隔离级别时,应用程序的性能将降低。

  • Read uncommitted - 该选项仅适用于具有非共享数据的非任务关键型系统(这在应用程序中是很少见的情况)。性能处于最佳状态,但是将牺牲并发控制。如果确定没有其他并发事务,请使用该选项。使用该选项,以上所列的数据问题都无法解决。
  • Read committed - 这是大多数数据库的默认隔离级别。只能读取提交的数据,因此该选项解决了脏数据读问题。由于要求对数据库使用附加锁,因此性能将会慢一些。
  • Repeatable read - 通过使用该隔离级别,解决脏数据读和未提交读问题。可以保证读取的任何行可以在以后被重读而其值将不会改变。
  • Serializable - 这是最严格的隔离级别,解决了所有三个数据问题。在希望事务以真正隔离的方式运行并完全与其他事务独立时,请使用该级别。这将保证数据一致性。对任务关键型系统使用它来保证真正地隔离事务行为。但是注意,该隔离级别是以性能为代价。
隔离级别对应能解决的一致性问题
read uncommittedread committedRepeatable readSerializable
解决脏数据读
解决不可重复读
解决影像读
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值