Update 数据库系统原理.md
This commit is contained in:
parent
93a9fe11cb
commit
4b0db3f578
|
@ -389,11 +389,11 @@ MVCC 不能解决幻读的问题,Next-Key Locks 就是为了解决这个问题
|
|||
|
||||
## Gap Locks
|
||||
|
||||
锁定一个范围内的索引,例如当一个事务执行以下语句,其它事务就不能在 t.c 中插入 15。
|
||||
间隙锁锁住的是多行,是一个数据范围。间隙锁主要是为了防止出现幻读,但是它会把锁定范围扩大,有时候也会给我们带来麻烦。在数据库参数中,控制间隙锁的参数是 ```innodb_locks_unsafe_for_binlog```, 这个参数默认值是 OFF,也就是启用间隙锁,它是一个bool值,当值为 true 时表示 disable 间隙锁。那为了防止间隙锁是不是直接将 ```innodb_locaks_unsafe_for_binlog``` 设置为 ```true``` 就可以了呢?不一定!而且这个参数会影响到主从复制及灾难恢复,这个方法还尚待商量。
|
||||
|
||||
```sql
|
||||
SELECT c FROM t WHERE c BETWEEN 10 and 20 FOR UPDATE;
|
||||
```
|
||||
间隙锁的出现主要集中在同一个事务中先 delete 后 insert 的情况下,当我们通过一个参数去删除一条记录的时候,如果参数在数据库中存在,那么这个时候产生的是普通行锁,锁住这个记录,然后删除,最后释放锁。如果这条记录不存在,问题就来了,数据库会扫描索引,发现这个记录不存在,这个时候的 delete 语句获取到的就是一个间隙锁,然后数据库会向左扫描扫到第一个比给定参数小的值,向右扫描扫描到第一个比给定参数大的值,然后以此为上下界限构建一个区间,进而锁住整个区间内的数据,一个特别容易出现死锁的间隙锁诞生了。
|
||||
|
||||
通过修改 ```innodb_locaks_unsafe_for_binlog``` 参数来取消间隙锁从而达到避免这种情况的死锁的方式尚待商量,那就只有修改代码逻辑,存在才删除,尽量避免去删除不存在的记录。
|
||||
|
||||
## Next-Key Locks
|
||||
|
||||
|
|
Loading…
Reference in New Issue
Block a user