MySQL之事务,锁, MVCC

1.什么是事务?

一组逻辑操作单元,使数据从一种状态变换到另一种状态

2.事务的ACID特性

  • 原子性

指事务是一个不可分割的工作单位,要么全部提交,要么全部失败回滚

  • 一致性

事务执行前后,数据从一个合法性状态变换到另一个合法性状态。这种状态跟具体的业务有关,通俗的说,这状态是你自己定义的,满足这个状态,数据就是一致的,不满足这个状态,就是不一致的

  • 隔离性

指一个事务的执行不能被其他事务干扰,即一个事务的内部操作及使用的数据对并发的其他事务是隔离的,并发执行的各个事务之间不能互相干扰

  • 持久性

指一个事务一旦被提交,它在数据库中对数据的改变是永久性的,接下来的其他操作和数据库的故障不应该对其有任何影响

事务的隔离性由锁机制实现,而事务的原子性,一致性和持久性由事务的redo日志和undo日志来保证

3.SQL中的四种隔离级别

  • READ UNCOMMITTED:读未提交
  • READ COMMITTED:读已提交
  • REPETABLE READ:可重复读(默认隔离级别)
  • SERIALIZABLE:可串行化

4.MySQL锁的分类

  • 从数据操作的粒度划分:表级锁,行级锁,页级锁

表锁

(1)表级别的S锁,X锁

(2)意向锁

(3)自增锁

(4)元数据锁

行锁

(1)记录锁

仅仅把一条记录锁上

(2)间隙锁

MySQL在默认隔离级别下是可以解决幻读问题的,解决方案有两种,可以使用MVCC方案,也可以采用加锁方式解决(间隙锁),间隙锁的提出仅仅是为了防止插入幻影记录而提出的。

(3)临键锁

有时候我们既想锁住某条记录,又想阻止其他事务在该记录的前边间隙插入新纪录,所以InnoDB提出临键锁。临键锁是在存储引擎 InnoDB,事务级别在可重复读的情况下使用的数据库锁,也是InnoDB引擎默认的锁。

(4)插入意向锁

  • 从对待锁的态度划分:乐观锁,悲观锁

    悲观锁总是假设最坏的情况,每次拿数据的时候都认为别人会修改,所以每次在拿数据的时候都会上锁,这样别人想拿到这个数据就会阻塞。比如行锁,表锁,读锁,写锁等,都是在做操作之前上锁。Java中的synchronized和ReentrantLock等独占锁就是悲观锁思想的实现。悲观锁适合写操作多的场景。

    乐观锁不用每次都对数据上锁,但是在更新的时候会判断一下此期间别人有没有更新这个数据。乐观锁不采用数据库自身的锁机制,而是通过程序去实现的。可以使用版本号机制CAS实现。乐观锁适用于多读的情形,可以提高吞吐量。

  • 按加锁的方式划分:显示锁,隐式锁
  • 全局锁
  • 死锁

5.MVCC

查询一条记录的时候,系统如何通过MVCC找到它:

1. 首先获取事务自己的版本号,也就是事务 ID;
2. 获取 ReadView;
3. 查询得到的数据,然后与 ReadView 中的事务版本号进行比较;
4. 如果不符合 ReadView 规则,就需要从 Undo Log 中获取历史快照;
5. 最后返回符合规则的数据。

在隔离级别为读已提交(Read Committed)时,一个事务中的每一次 SELECT 查询都会重新获取一次ReadView。而在可重复读的隔离级别下,一个事务只在第一次SELECT的时候会获取一次ReadView,而后面所有的SELECT都会复用这个ReadView,通过ReadView规则机制解决了幻读的问题。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值