MySql的锁机制简单梳理

引言

本篇博客主要是简单梳理mysql锁相关理论知识,并没有深入解释其中的实现原理,可能会有一点简单的加锁机制。

博主在工作时接触到一些数据库锁的相关知识,尤其是事务和锁的关系比较密切,比如间隙锁和MVCC....等,大佬可全部忽略,部分知识取自《MySQL高性能书籍_第3版(中文)》,说实话在阅读本书之前还比较有信心,然后第一章的存储引擎和mysql逻辑架构就花费了大量时间去理解和学习,因为很多知识是相互依赖的,读懂需要大量的知识储备和工作经验吧。另外有不足之处还请不吝赐教。

锁的分类

从mysql锁大的层面上看,所还是分为两类,悲观锁和乐观锁。

大致屡一下分层和分类

乐观锁
    -- 使用Version字段自旋实现,更新前先查版本,更新前先判断版本

悲观锁
    -- 行锁 (Innodb特有)
        -- 读锁,写锁
    -- 表锁 (由MySql源码实现)
        -- 读锁,写锁

这里解释一下有些博客和资料中的分类是有差异的,记得有一篇博客说表锁属于乐观锁误导了我,在面试时面试官问了我这个问题我说属于乐观锁他又问了一下你确定吗...我就知道错了。

乐观锁

(Optimistic Concurrency Control,OCC):假设不会发生并发冲突,只在提交操作时检查是否违反数据完整性。也没具体指定怎么检查。

悲观锁

(Pessimistic Concurrency Control,PCC):假定会发生并发冲突,屏蔽一切可能违反数据完整性的操作。

相比大多数程序员对这两种锁概念比较清晰,不多赘述。

那么主要的问题是行锁和表锁。

行锁

支持行锁的存储引擎有主流的InnoDb,XtarDb等

行锁的劣势:开销大;加锁慢;会出现死锁

行锁的优势:锁的粒度小,发生锁冲突的概率低;处理并发的能力强

行锁本身支持的并发比表锁高,但是换来的缺点是效率问题,带来了巨大的锁开销,行锁只是在存储引擎中实现的而与mysql架构曾没有任何关系,说的直白一点就是mysql并不关心存储引擎的锁实现机制,只是存储引擎本身实现了行锁。

行锁的读写锁机制

行锁本身为小粒度锁,所以相应的读写锁没有那么多限制,在增删改操作时会使用锁定行数据,查询时会使用读锁锁定行数据,写锁为排他锁,可以理解为单线程操作行数据,读锁为共享锁支持多数据访问行。而InnoDB支持表锁和行锁,在有索引条件的语句操作中会使用行锁,若没有索引操作或是全表扫描时InnoDB会使用表锁。

表锁

表锁本身是mysql架构实现的而并非某一存储引擎,大家口中的MyISAM的表锁并不是存储引擎去具体实现的。

表锁的劣势:锁力度大,锁冲突几率大,支持并发低

表锁的优势:开销小,枷锁快,不会死锁

表锁是MySql的基本策略,也是开销最小的锁策略。

表锁的读写锁机制

表锁本身粒度比较大,所以面临的冲突也比较多,在增删改操作时加写锁,此时会阻塞其他读写操作,而表锁的写锁却又更高的优先级,例如有读锁在队列中,会被写锁有线执行。

读写锁

读写锁是并发控制中的经典解决方案,读锁就是共享锁,写锁就是排他锁。

共享锁可以理解为多个客户读取同一个资源,他们互不干扰。

排他锁会锁定当前要修改的资源,禁止其他用户修改和访问此资源,保证资源的唯一性,防止多个用户修改同

一资源

posted @ 2020-12-25 16:41  一半人生  阅读(172)  评论(0编辑  收藏  举报