MySQL锁


<br>

1. 表锁

表锁分为写锁,读锁,二者读读不阻塞,读写阻塞,写写阻塞

<br> <br>

2. 行锁

行锁分为共享锁,排他锁,即读锁和写锁

多粒度锁机制自动实现表、行锁共存,InnoDB内部有意向表锁

  • 意向共享锁(IS):事务在给一个数据行加共享锁前必须先取得该表的IS锁。
  • 意向排他锁(IX):事务在给一个数据行加排他锁前必须先取得该表的IX锁。

<br> <br>

3. 表、行锁区别

表锁:开销小,加锁快;不会出现死锁;锁定力度大,发生锁冲突概率高,并发度最低

行锁:开销大,加锁慢;会出现死锁;锁定粒度小,发生锁冲突的概率低,并发度高

  • InnoDB会自动给UPDATE、DELETE、INSERT加排他锁(X)
  • InnoDB查找时,只有用到了索引才加行锁,否则加表锁
  • MyISAM会自动给SELECT加读锁,自动给UPDATE、DELETE、INSERT加写锁
  • MyISAM查询和插入可以并发,若表中没有被删除的行,可在一个进程读表的同时,另一个进程从表尾插入数据,InnoDB不行
  • mysql中同时加锁,写锁优先于读锁

<br> <br>

4. MVCC

锁的应用最终导致不同事务的隔离级别、而MVCC多版本并发控制,通过增加版本的形式实现两种隔离级别(不使用到锁),MVCC读写不阻塞,是行级锁的升级

隔离分为语句级Readcommitted隔离级别和事务级Repeatableread隔离级别

<br>

语句级:

事务A读取数据生成版本号

事务B修改数据(加了写锁)

事务A再读取数据时,是读取最新版本号的(若事务B提交了生成新版本号,没有提交则还是原来的版本号)

这里出现了不可重复读,事务A数据根据事务B而改变

<br>

事务级:

事务A读取数据生成版本号1

事务B修改数据生成新版本2

事务A再读取数据还是用版本号1

避免了不可重复读,出现了幻读

MySQL的 Repeatableread隔离级别加上GAP间隙锁解决了幻读,不需要串行了

<br> <br>

5. 乐观锁和悲观锁

丢失更新:一个事务的更新覆盖了其它事务的更新结果的解决方法:

  • 使用Serializable隔离级别,事务是串行执行的,并发低
  • 乐观锁
  • 悲观锁
<br>

**乐观锁:**要在表中设计一个版本字段。第一次要获取这个字段,处理完业务逻辑开始更新时,要对比现在的版本字段和第一次的版本字段是否相同,相同则更新反之拒绝。这里没有给数据库加锁,需要我们手动操作

UPDATE <表名> SET name="Howl",version=version+1 WHERE ID=#{id} AND version=#{version}
<br>

**悲观锁:**是数据库层面加锁,相当于排他锁,其他的事务就不能对它修改了,需要等待当前事务修改完之后才可以修改,在 select 语句后面加 FOR UPDATE

1# 需要在事务中加,因为select是不加任何行锁的 2SELECT * FROM <表名> FOR UPDATE / LOCK IN SHARE MODE

<br> <br>

6. 间隙锁GAP

在范围查找时若请求写锁或读锁,InnoDB会给符合范围条件的已有数据的索引项加锁

对于键值在条件范围内但并不存在的记录,叫做间隙

间隙锁只会在Repeatableread及以下隔离级别使用,作用于防止幻读

<br> <br>

点赞
收藏

评论区

加载中...

相关推荐

MySQL:[Err] 1292 - Incorrect datetime value: ‘0000-00-00 00:00:00‘ for column ‘CREATE_TIME‘ at row 1

文章目录问题用navicat导入数据时,报错:原因这是因为当前的MySQL不支持datetime为0的情况。解决修改sql\mode:sql\mode:SQLMode定义了MySQL应支持的SQL语法、数据校验等,这样可以更容易地在不同的环境中使用MySQL。全局s

Oracle 分组与拼接字符串同时使用

SELECTT.,ROWNUMIDFROM(SELECTT.EMPLID,T.NAME,T.BU,T.REALDEPART,T.FORMATDATE,SUM(T.S0)S0,MAX(UPDATETIME)CREATETIME,LISTAGG(TOCHAR(

皕杰报表之UUID

​在我们用皕杰报表工具设计填报报表时,如何在新增行里自动增加id呢?能新增整数排序id吗?目前可以在新增行里自动增加id,但只能用uuid函数增加UUID编码,不能新增整数排序id。uuid函数说明:获取一个UUID,可以在填报表中用来创建数据ID语法:uuid()或uuid(sep)参数说明:sep布尔值,生成的uuid中是否包含分隔符'',缺省为

mysql主从数据对比工具简介

1Checksum1.1checksum原理checksumtable的原理是对表中的数据进行一行一行的较验和计算,在执行checksum命令时,表会被加一个读锁(readlock),因此对于大表,这是一个很耗时的过程。读锁:又叫S锁/共享锁;当MySQL

MySQL 中的共享锁和排他锁的用法

在MySQL中的行级锁、表级锁和页级锁中,咱们介绍过,行级锁是MySQL中锁定粒度最细的一种锁,行级锁能大大减少数据库操作的冲突。行级锁分为共享锁和排他锁两种,本文将详细介绍共享锁和排他锁的概念、使用方式及注意事项。共享锁(ShareLock)共享锁又称读锁,是读取操作创建的锁。其他用户可以并发读取数据,但任

MySQL中的共享锁与排他锁

在MySQL中的行级锁,表级锁,页级锁(https://www.oschina.net/action/GoToLink?urlhttp%3A%2F%2Fwww.hollischuang.com%2Farchives%2F914)中介绍过,行级锁是Mysql中锁定粒度最细的一种锁,行级锁能大大减少数据库操作的冲突。行级锁分为共享锁和排他锁两种,本文将详细

MySQL锁 - HelloWorld