首页 > 数据库 >MySQL锁机制揭秘:从行锁到表锁,共享锁到排他锁,悲观锁到乐观锁的全面解读

MySQL锁机制揭秘:从行锁到表锁,共享锁到排他锁,悲观锁到乐观锁的全面解读

时间:2024-09-15 23:24:58浏览次数:10  
标签:加锁 从行 更新 锁到 线程 MySQL 余额 操作 数据

MySQL有哪些锁

1、按照锁的粒度划分

行锁

是最低粒度的的锁,锁住指定行的数据,加锁的开销较大,加锁较慢,可能会出现死锁的情况,锁的竞争度会较低,并发度相对较高。但是如果where条件里的字段没有加索引,则加的行锁会自动升级为表锁,因为行锁是基于索引去进行操作的,所以想要加行锁,就一定要在条件字段为索引的基础上进行操作。

表锁

锁住指定的表,粒度较大,但是加锁的开销小,加锁快,不会出现死锁,且锁的竞争度会较为激烈,并发度比行锁要低很多。

全局锁

粒度最大的锁,会锁住整个库,所有的表都不能进行更新插入操作,只能读。

全局锁命令如下:

flush tables with read lock;

页锁(仅了解即可,几乎用不到)

是仅在BDB(Blackhole黑洞)引擎上所支持的一种锁。页锁就是在数据页上,以页为维度进行锁定的,一页里面会有多行数据。页锁的开销是介于行锁和表锁之间的,并发度一般。

2、按照互斥性划分

共享锁(读锁)

一个事务给某行数据加上共享锁之后,其他事务就不能再加拍排他锁,但是可以加共享锁。因为读操作不会去改变数据信息,所以可以允许多个事务去共享同一个共享锁,并行去读取数据,而不会互相影响。

排他锁(写锁)

一个事务给某行数据加上排他锁之后,其他事务就不能再给这行数据加任何锁,即不允许写,也不允许读。所以排他锁可以确保在同一时刻,一个被加上锁的资源只会有一个事务去进行更新操作,有效避免了多个事务同时对一条数据进行修改,导致最终出现数据不一致问题。

3、按照性能划分

注意:乐观锁、悲观锁、意向锁都不是mysql里实际上真正的锁,而是由开发人员定义出来区分两种类型锁的设计思想。

悲观锁(PCC)

悲观锁(Pessimistic Concurrency Control)的思想是,持有一种很悲观消极的态度,默认为在数据资源被外部访问时,一定会出现冲突,所以在一个线程在数据处理的过程中都会持有锁资源,保证在同一时刻,只有一个线程可以访问到这个数据,具有排他性。

一般悲观锁都是直接使用mysql数据库的行锁和表锁去实现。

乐观锁(OCC)

乐观锁(Optimistic Concurrency Control)的思想是,持有一种乐观的态度,认为即使是在并发的场景下,对于数据资源的访问,也不会出现冲突,所以不会去加锁,而是在数据进行提交更新操作的时候,才会去判断此次提交是否存在冲突,如果冲突了,便在代码逻辑层面去处理冲突之后的处理方案,是直接结束本次更新操作,还是重新再去尝试更新。

例如

user表有数据id为1,balance余额为10。

现在想实现在并发的场景下,去修改余额(线程A请求,需要扣减余额3,线程B请求,需要扣减余额9),需要避免出现余额为负数。

实现方案,给user表加一个版本号字段version,每次更新数据时,数据更新行的version版本号要加1,且在执行更新操作的时候,where条件里需要带上版本号。

操作流程

请添加图片描述

详细过程解析

线程A和线程B同时获取到用户的余额为10,数据版本为1。

然后线程A先执行了更新操作,将用户的余额改成了7(线程A要扣减余额3),数据版本也变成了2。

紧接着线程B也来执行更新操作了,但是因为线程B查询用户余额时,线程A还没有更新数据,所以线程B要将用户的余额改成1(线程B要扣减余额9)。

但是在更新时,因为线程B拿到的数据版本是1,而此时的数据版本已经成为了2,所以线程B的更新操作失败了。

此时线程B接收到更新操作失败的结果后,可以选择直接抛出异常给用户,或者重新查询用户余额之后,再去尝试扣减余额操作。

意向锁(仅了解即可)

意向锁可简单理解为在操作行锁时,在表上添加了一个标识,表明这个表已经存在了共享锁或排他锁,其他事务在想加锁时,只需要到表上判断下这个标识就知道自己能否继续往下获取到锁。

深入了解可看文章 《 深度解读MySQL意向锁的工作原理机制与应用场景

间隙锁(Gap-Lock)

间隙锁是InnoDB在可重复读的隔离级别下,为了解决幻读而引入的一种锁机制。

间隙锁只会在数据表的隔离级别为可重复读隔离级别下才能生效。

是在索引记录之间的间隙上加的一个锁,是锁定了一个数据区间,比如一数据表的字段a数据为[1, 2, 5, 9],如果sql如下

select * from tablename where a = 3 for update;

,则加的间隙锁就是[2, 5],间隙的范围是根据检索条件向下寻找最靠近检索条件的记录值A,用于作为左区间,向上寻找最靠近检索条件的记录值B,用于作为右区间,即锁定的间隙为(A,B)。加上了间隙锁,则[2, 5]区间的数据都不能再进行操作,直到锁释放。

4、加锁方式

查询语句加共享锁

# 如果id有索引,则是加的行级共享锁,如果id没有索引,则加的是表级共享锁
select * from tablename where id = 'xxxx' lock in share mode;

查询语句加排他锁

# 如果id有索引,则是加的行级排他锁,如果id没有索引,则加的是表级排他锁
select * from tablename where id = 'xxxx' for update

在操作delete、update、insert语句时,数据库会自动加上排他锁(如果条件有索引,则是加的行级锁,如果条件没有索引,则加的是表级锁)。

请添加图片描述

关注我,我将持续输出Java常用相关技术文章。

标签:加锁,从行,更新,锁到,线程,MySQL,余额,操作,数据
From: https://blog.csdn.net/qq_38038472/article/details/142177883

相关文章

  • 一文看完MySQL 9.0新特性!
    本文总结自MySQL8.4以来,在MySQL9.0中新增、废弃、更改和删除的内容。MySQL9.0中新增或更改的功能。1MySQL9.0新特性1VECTOR类型支持MySQL9.0支持VECTOR列类型。向量是一个数据结构,它由条目列表(4字节浮点值)组成,可以表示为二进制字符串值或列表格式字符串。VECT......
  • mysql学习教程,从入门到精通,TOP 和MySQL LIMIT 子句(15)
    1、TOP和MySQLLIMIT子句内容在SQL中,不同的数据库系统对于限制查询结果的数量有不同的实现方式。TOP关键字主要用于SQLServer和Access数据库中,而LIMIT子句则主要用于MySQL、PostgreSQL(通过LIMIT/OFFSET语法)、SQLite等数据库中。下面将分别详细介绍这两个功能......
  • MySQL间隙锁,next-key锁
    间隙锁间隙锁是对索引记录之间的间隙的锁,或者是对第一个索引记录之前或最后一个索引记录之后的间隙的锁。例如,SELECTc1FROMtWHEREc1BETWEEN10and20FORUPDATE;阻止其他事务将的值插入15到列中t.c1,无论列中是否已经存在任何此类值,因为该范围内所有现有值之间的......
  • MySQL练手题--体育馆的人流量(困难)
    一、准备工作CreatetableIfNotExistsStadium(idint,visit_dateDATENULL,peopleint);TruncatetableStadium;insertintoStadium(id,visit_date,people)values('1','2017-01-01','10');insertintoStadium(id,visit_date,......
  • mysql事务
    MySQL事务是数据库管理系统(DBMS)中的一项关键功能,确保一系列数据库操作作为一个整体被执行,且具有原子性、一致性、隔离性和持久性(ACID)的特性。事务处理机制可以帮助开发者确保数据的完整性和一致性,特别是在出现错误或并发操作时。1.事务的四大特性(ACID)原子性......
  • mySql 添加新用户
    运行以下SQL语句来创建新用户并设置密码:INSERTINTOmysql.user(User,Host,Password)VALUES('用户名','主机名',PASSWORD('密码'));其中,'用户名'为新用户的名称,     '主机名'为允许该用户连接的主机,可以使用通配符'%'表示允许从任何主机连接,    ......
  • 【MySQL】MySQL索引与事务的透析——(超详解)
    前言......
  • mysql数据怎么导入到帝国cms
    将MySQL数据导入到帝国CMS中通常有两种情况:一种是从现有的MySQL数据库导入数据到帝国CMS的新建数据库中,另一种是从帝国CMS的备份文件恢复数据到现有的帝国CMS数据库中。以下是针对这两种情况的具体步骤:从现有MySQL数据库导入数据到帝国CMS方法一:手动迁移数据导出现有数据库:......
  • VPS Ubuntu22.04 安装WordPress 搭建网站 详细全流程(基于Apache+MySQL+PHP)(二)
    VPSUbuntu22.04安装WordPress搭建网站详细全流程(基于Apache+MySQL+PHP)(二)简介在网站处理和网络管理方面,WordPress是用户可以采取的最明智的选择。由于WordPress的巨大优势,它在网页设计师中广受欢迎。统计数据显示,访问量最大的1000个网站中约有35%是WordPress。......
  • MySQL 大表拆分
    概述在实际工作中,在关系数据库(MySQL、PostgreSQL)的单表数据量上亿后,往往会出现查询和分析变慢甚至无法执行统计分析的情况。这时就需要将大表拆分为多个小表,将小表分布在多个数据库上,形成一个数据库集群。这样的话,一条SQL统计语句就可以在多台服务器上并发执行,然后将执行结果汇......