-
Notifications
You must be signed in to change notification settings - Fork 0
07 | 行锁功过:怎么减少行锁对性能的影响? #16
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
死锁检测是每条事务执行前都会进行检测吗?如果要加锁访问的行上有锁才要检测。一致性读不会加锁,就不需要做死锁检测; 并不是每次死锁检测都都要扫所有事务。比如某个时刻,事务等待状态是这样的: B 在等 A, D 在等 C,现在来了一个 E,发现 E 需要等 D,那么 E 就判断跟 D、C 是否会形成死锁,这个检测不用管 B 和 A |
表锁同一张表在同一时刻只能有一个更新。但是表级锁中的 MDL 锁,DML 语句会产生 MDL 读锁,而MDL 读锁不是互斥的,也就是说一张表可以同时有多个 DML 语句操作。这两种说法是否矛盾?不矛盾,MDL 锁和表锁是两个不同的结构 |
多种锁同时存在时,以粒度最小的锁为准么?如果有多种锁,必须得“全部不互斥”才能并行,只要有一个互斥,就得等 |
当备库用–single-transaction 做逻辑备份的时候,如果从主库的 binlog 传来一个 DDL 语句会怎样?
在备份开始的时候,为了确保 RR(可重复读)隔离级别,再设置一次 RR 隔离级别 (Q1);
|
行锁
MySQL 的行锁是由存储引擎实现的,行锁就是针对数据表中行记录的锁。
行锁比表锁的粒度小,发生锁争用的可能小,并发度高。但行锁比表锁开销大,因为锁的各种操作(包括获取锁、释放锁、以及检查锁状态)都会增加系统开销。
InnoDB 行锁是通过给索引上的索引项加锁来实现的。所以,只有通过索引条件检索数据,InnoDB 才使用行级锁,否则,InnoDB 将使用表锁
从两段锁说起
InnoDB 事务中,行锁是在需要的时候才加上,等到事务结束之后才释放,这就是两阶段锁协议。
根据两阶段锁协议,在事务中如果需要锁多个行,要把最可能造成锁冲突、影响并发度的行往后放。
死锁和死锁检测
当并发系统中不同线程出现循环资源依赖,涉及的线程都在等待别的线程释放资源时,就会导致这几个线程都进入无限等待的状态,称为死锁。
当出现死锁以后,有两种策略:
innodb_lock_wait_timeout
来设置。innodb_deadlock_detect
设置为 on,表示开启这个逻辑。在 InnoDB 中,
innodb_lock_wait_timeout
的默认值是 50s,这个等待时间长得无法接受;但是如果将这个参数设置得过小,那么 InnoDB 可能就分不清锁等待和死锁。所以,第二种策略是比较常用的:主动监测死锁。但是第二种策略也会面临一个问题:死锁检测可能会极大耗费 CPU 资源。
死锁检测的一般过程是:每当一个事务被锁的时候,就要看看它所依赖的线程有没有被别人锁住,如此循环,最后判断是否出现了循环等待,也就是死锁。
怎么解决由热点行更新导致的性能问题呢?
The text was updated successfully, but these errors were encountered: