mysql的事务和数据库锁的关系
数据库加事务并不是数据就安全来了,事务和锁要分析清楚和配合使用
问题背景处于对高并发的秒杀环节的理解整理如下:
秒杀的时候高并发主要注意
1、在秒杀的情况下,肯定不能如此高频率的去读写数据库,会严重造成性能问题的
必须使用缓存,将需要秒杀的商品放入缓存中,并使用锁来处理其并发情况。当接到用户秒杀提交订单的情况下,先将商品数量递减(加锁/解锁)后再进行其他方面的处理,处理失败在将数据递增1(加锁/解锁),否则表示交易成功。
当商品数量递减到0时,表示商品秒杀完毕,拒绝其他用户的请求。
2、这个肯定不能直接操作数据库的,会挂的。直接读库写库对数据库压力太大,要用缓存。
把你要卖出的商品比如10个商品放到缓存中;然后在memcache里设置一个计数器来记录请求数,这个请求书你可以以你要秒杀卖出的商品数为基数,比如你想卖出10个商品,只允许100个请求进来。那当计数器达到100的时候,后面进来的就显示秒杀结束,这样可以减轻你的服务器的压力。然后根据这100个请求,先付款的先得后付款的提示商品以秒杀完。
3、首先,多用户并发修改同一条记录时,肯定是后提交的用户将覆盖掉前者提交的结果了。
这个直接可以使用加锁机制去解决,乐观锁或者悲观锁。
乐观锁,就是在数据库设计一个版本号的字段,每次修改都使其+1,这样在提交时比对提交前的版本号就知道是不是并发提交了,但是有个缺点就是只能是应用中控制,如果有跨应用修改同一条数据乐观锁就没办法了,这个时候可以考虑悲观锁。
悲观锁,就是直接在数据库层面将数据锁死,类似于oralce中使用select xxxxx from xxxx where xx=xx for update,这样其他线程将无法提交数据。
除了加锁的方式也可以使用接收锁定的方式,思路是在数据库中设计一个状态标识位,用户在对数据进行修改前,将状态标识位标识为正在编辑的状态,这样其他用户要编辑此条记录时系统将发现有其他用户正在编辑,则拒绝其编辑的请求,类似于你在操作系统中某文件正在执行,然后你要修改该文件时,系统会提醒你该文件不可编辑或删除。
4、不建议在数据库层面加锁,建议通过服务端的内存锁(锁主键)。当某个用户要修改某个id的数据时,把要修改的id存入memcache,若其他用户触发修改此id的数据时,读到memcache有这个id的值时,就阻止那个用户修改。
5、实际应用中,并不是让mysql去直面大并发读写,会借助“外力”,比如缓存、利用主从库实现读写分离、分表、使用队列写入等方法来降低并发读写。
mysql
-----MyISAM引擎:
使用的是表级锁。理解为锁住整个表,可以同时读,写不行。
----innoDB
使用的是行级锁,它也支持表级锁。单独的一行记录加锁 。
事务和数据库锁的关系如下
读操作可以分成两类:快照读 (snapshot read)与当前读 (current read)。
快照读,读取的是记录的可见版本 (有可能是历史版本),不用加锁。
当前读,读取的是记录的最新版本,并且,当前读返回的记录,都会加上锁,保证其他事务不会再并发修改这条记录。
锁类型
共享锁(S锁):假设事务T1对数据A加上共享锁,那么事务T2可以读数据A,不能修改数据A。
排他锁(X锁):假设事务T1对数据A加上共享锁,那么事务T2不能读数据A,不能修改数据A。
我们通过update、delete等语句加上的锁都是行级别的锁。只有LOCK TABLE … READ和LOCK TABLE … WRITE才能申请表级别的锁。
当执行select 的时候 默认是不加锁的 (快照读) (这种说法在隔离级别为Serializable中不成立)
如果想要对某个行数据加锁需要 执行如下:
select * from table where num = 200 lock in share mode 共享锁
select * from table where num = 200 for update 行级锁
这是通过显示加锁实现的
当执行update,insert,delete的时候 默认是加行锁的
Cluster Index:聚簇索引
InnoDB存储引擎的数据组织方式,是聚簇索引表:完整的记录,存储在主键索引中,通过主键索引,就可以直接获取记录所有的列。
Read Uncommited(RU):读未提交,一个事务可以读到另一个事务未提交的数据!
Read Committed (RC):读已提交,一个事务可以读到另一个事务已提交的数据!
Repeatable Read (RR):可重复读,加入间隙锁,一定程度上避免了幻读的产生!注意了,只是一定程度上,并没有完全避免!我会在下一篇文章说明!另外就是记住从该级别才开始加入间隙锁(这句话记下来,后面有用到)!
Serializable:串行化,该级别下读写串行化,且所有的select语句后都自动加上lock in share mode,即使用了共享锁。因此在该隔离级别下,使用的是当前读,而不是快照读。
完全串行化的读,每次读都需要获得表级共享锁,读写相互都会阻塞
完全串行化的读,每次写都需要获得所有行级锁,读写相互都会阻塞
RC/RU+条件列非索引
select * from table where num = 200 lock in share mode 共享锁
select * from table where num = 200 for update 行锁
RR/Serializable+条件列非索引
select * from table where num = 200
在RR级别下,不加任何锁,是快照读。(可重读的时候也不加锁)
在Serializable级别下 ,完全串行化的读,每次读都需要获得表级共享锁,读写相互都会阻塞
select * from table where num = 200 lock in share mode
在Serializable级别下, 全表所有记录都加共享锁
select * from table where num = 200 for update
在Serializable级别下, 全表所有记录都加上行锁
所以:Serializable 都是表锁
参见:https://www.cnblogs.com/rjzheng/p/9950951.html,https://blog.csdn.net/xf552527/article/details/78811262
以上是对事务和锁的理解
参见:https://fengberlin.github.io/post/seckill/ 高并发处理思路,https://blog.csdn.net/GallenZhang/article/details/78626730
mysql的事务和数据库锁的关系的更多相关文章
- 数据库MySQL之 视图、触发器、存储过程、函数、事务、数据库锁、数据库备份、事件
数据库MySQL之 视图.触发器.存储过程.函数.事务.数据库锁.数据库备份.事件 浏览目录 视图 触发器 存储过程 函数 事务 数据库锁 数据库备份 事件 一.视图 1.视图概念 视图是一个虚拟表, ...
- MySQL的事务机制和锁(InnoDB引擎、MVCC多版本并发控制技术)
一.事务(数据库的事务都通用的定义) 1.1 事务定义 事务是由一步或几步数据库操作序列组成逻辑执行单元,这系列操作要么全部执行,要么全部放弃执行.事务通常以 BEGIN TRANSACTION 开始 ...
- MySql的隔离级别和锁的关系
一.事务的4个基本特征 Atomic(原子性): 事务中包括的操作被看做一个逻辑单元.这个逻辑单元中的操作要 么所有成功.要么所有失败. Consistency(一致性): 仅仅有合法的数据能 ...
- MySQL之视图、触发器、存储过程、函数、事务、数据库锁
一.视图 视图:是一个虚拟表,其内容由查询定义.同真实的表一样,视图包含一系列带有名称的列和行数据. 视图的特点: 1.视图的列可以来自不同的表,是表的抽象和逻辑意义上建立的新关系: 2.视图是由基本 ...
- mysql高级教程(三)-----数据库锁、主从复制
锁 概念 锁是计算机协调多个进程或线程并发访问某一资源的机制. 在数据库中,除传统的计算资源(如CPU.RAM.I/O等)的争用以外,数据也是一种供许多用户共享的资源.如何保证数据并发访问的一致性. ...
- 重新学习MySQL数据库9:Innodb中的事务隔离级别和锁的关系
重新学习MySQL数据库9:Innodb中的事务隔离级别和锁的关系 Innodb中的事务隔离级别和锁的关系 前言: 我们都知道事务的几种性质,数据库为了维护这些性质,尤其是一致性和隔离性,一般使用加锁 ...
- MySQL InnoDB中的事务隔离级别和锁的关系
前言: 我们都知道事务的几种性质,数据库为了维护这些性质,尤其是一致性和隔离性,一般使用加锁这种方式.同时数据库又是个高并发的应用,同一时间会有大量的并发访问,如果加锁过度,会极大的降低并发处理能力. ...
- MySQL数据库 InnoDB引擎 事务及行锁总结
一.事务 1.事务的四大特性 (1)原子性:事务开始后所有的操作要么一起成功,要么一起失败,整个事务是一个不可分割的整体. (2)一致性:是物开始前到结束后,数据库的完整性约束没有被破坏. (3)隔离 ...
- [数据库事务与锁]详解五: MySQL中的行级锁,表级锁,页级锁
注明: 本文转载自http://www.hollischuang.com/archives/914 在计算机科学中,锁是在执行多线程时用于强行限制资源访问的同步机制,即用于在并发控制中保证对互斥要求的 ...
随机推荐
- Java Script--------问题错误解决意外的终止输入Uncaught SyntaxError: Unexpected end of input解决办法
错误信息: Uncaught SyntaxError: Unexpected end of input 错误原因: 一般是成对的符号只出现了单只,比如说“”,‘’,{},[]. 解决办法:检查符号是否 ...
- JAVA 平时作业二
编写一个 Java 应用程序,统计数组{1,3,4,7,2,1,1,5,2,5,7,2,1,1,3},统 计显示每种数字其出现的次数以及出现最多和最少次数的数字 public class Number ...
- Can peel peel solve pesticide problem
Can peel peel solve pesticide problem? Middle peasants medicinal modern agriculture more and more, t ...
- selenium中下拉框的定位
from selenium import webdriverfrom selenium.webdriver.support.select import Selectimport timedriver ...
- 泊爷带你学go -- 经典的继承与接口 简直吊炸天 !
package main import ( "fmt" ) type TeamBase struct { m_TeamId uint64 m_Rid uint32 m_RoomRu ...
- vue启动报错
在安装依赖后,启动时报错 修复方法:将项目node_modules文件夹删除掉,重新cnpm install即可
- C语言---指针变量详解3
指针可以指向一份普通类型的数据,例如 int.double.char 等,也可以指向一份指针类型的数据,例如 int *.double *.char * 等.如果一个指针指向的是另外一个指针,我们就称 ...
- c++ 第二章知识梳理
2.1.c++语言概括 2.1.1)c++的产生 一个更好的c,由c演变而来 2.1.2)c++的特点 一是尽量兼容c,二是支持面向对象的方法.更安全,且简洁高效. 2.1.3~2.1.5 多数和C相 ...
- 【笔记】.NET开发环境下使用PostgreSQL+Oracle_fdw 实现两个数据库之间数据交互操作(二)
一 新的可视化工具 因为前文所提到的,看不到外部服务器和外部表的问题,我更换了可视化工具. 好用的新工具PostgreSQL Maestro! 当然如此好用的工具不是免费的,如果想免费使用还请自己去找 ...
- [C# 基础知识系列]专题二:委托的本质论 (转载)
引言: 上一个专题已经和大家分享了我理解的——C#中为什么需要委托,专题中简单介绍了下委托是什么以及委托简单的应用的,在这个专题中将对委托做进一步的介绍的,本专题主要对委本质和委托链进行讨论. 一.委 ...