MYSQL的ACID
原子性 (Atomicity)
原子性是指一个事务是一个不可分割的工作单位,其中的操作要么都做,要么都不做。
隔离性 (Isolation)
隔离性是指多个事务并发执行的时候,事务内部的操作与其他事务是隔离的,并发执行的各个事务之间不能互相干扰。
持久性 (Durability)
持久性是指事务一旦提交,它对数据库的改变就应该是永久性的。接下来的其他操作或故障不应该对其有任何影响。
一致性 (Consistency)
一致性是指事务执行前后,数据处于一种合法的状态,这种状态是语义上的而不是语法上的。 这个状态是满足预定的约束就叫做合法的状态,再通俗一点,这状态是由你自己来定义的。满足这个状态,数据就是一致的,不满足这个状态,数据就是不一致的!
Mysql怎么保证一致性的?
从数据库层面,数据库通过原子性、隔离性、持久性来保证一致性。也就是说ACID四大特性之中,C(一致性)是目的,A(原子性)、I(隔离性)、D(持久性)是手段,是为了保证一致性,数据库提供的手段。数据库必须要实现AID三大特性,才有可能实现一致性。从应用层面,通过代码判断数据库数据是否有效,然后决定回滚还是提交数据。
Mysql怎么保证原子性的?
利用Innodb的undo log。 undo log名为回滚日志,是实现原子性的关键,当事务回滚时能够撤销所有已经成功执行的sql语句,他需要记录你要回滚的相应日志信息。
例如
(1)当你delete一条数据的时候,就需要记录这条数据的信息,回滚的时候,insert这条旧数据
(2)当你update一条数据的时候,就需要记录之前的旧值,回滚的时候,根据旧值执行update操作
(3)当年insert一条数据的时候,就需要这条记录的主键,回滚的时候,根据主键执行delete操作undo log记录了这些回滚需要的信息,当事务执行失败或调用了rollback,导致事务需要回滚,便可以利用undo log中的信息将数据回滚到修改之前的样子。
Mysql怎么保证持久性的?
利用Innodb的redo log(重做日志)。
正如之前说的,Mysql是先把磁盘上的数据加载到内存中,在内存中对数据进行修改,再刷回磁盘上。如果此时突然宕机,内存中的数据就会丢失。
怎么解决这个问题?
简单啊,事务提交前直接把数据写入磁盘就行啊。
这么做有什么问题?
只修改一个页面里的一个字节,就要将整个页面刷入磁盘,太浪费资源了。毕竟一个页面16kb大小,你只改其中一点点东西,就要将16kb的内容刷入磁盘,听着也不合理。
毕竟一个事务里的SQL可能牵涉到多个数据页的修改,而这些数据页可能不是相邻的,也就是属于随机IO。显然操作随机IO,速度会比较慢。
采用redo log解决上面的问题。当做数据修改的时候,不仅在内存中操作,还会在redo log中记录这次操作。当事务提交的时候,会将redo log日志进行刷盘(redo log一部分在内存中,一部分在磁盘上)。当数据库宕机重启的时候,会将redo log中的内容恢复到数据库中,再根据undo log和binlog内容决定回滚数据还是提交数据。
采用redo log的好处?
redo log进行刷盘比对数据页刷盘效率高,具体表现如下
redo log体积小,毕竟只记录了哪一页修改了啥,因此体积小,刷盘快。
redo log是一直往末尾进行追加,属于顺序IO。效率显然比随机IO来的快。
Mysql怎么保证隔离性的?
利用的是锁和MVCC机制。
MVCC,即多版本并发控制(Multi Version Concurrency Control),一个行记录数据有多个版本对快照数据,这些快照数据在undo log中。 如果一个事务读取的行正在做DELELE或者UPDATE操作,读取操作不会等行上的锁释放,而是读取该行的快照版本。
在事务隔离级别为读已提交(Read Commited)时,一个事务能够读到另一个事务已经提交的数据,是不满足隔离性的。但是当事务隔离级别为可重复读(Repeateable Read)中,是满足隔离性的。
MYSQL的ACID的更多相关文章
- mysql的ACID的理解
这是在网上copy下来的ACID的概念,可以直接跳过看后面: 1.原子性(Atomicity):事务开始后所有操作,要么全部做完,要么全部不做,不可能停滞在中间环节.事务执行过程中出错,会回滚到事务开 ...
- mysql 事物ACID和隔离级别
⑴ 原子性(Atomicity) 原子性是指事务包含的所有操作要么全部成功,要么全部失败回滚,这和前面两篇博客介绍事务的功能是一样的概念,因此事务的操作如果成功就必须要完全应用到数据库,如果操作失败则 ...
- MySQL——事务ACID&隔离级别
数据库事务ACID&隔离级别 什么是事务 事务是用户定义的一个数据库操作序列.这些操作要么全执行,要么全不执行,是一个不可分割的工作单元.在关系型数据库中,事务可以是一条SQL语句,也可以是一 ...
- 14.2.1 MySQL and the ACID Model
14.2 InnoDB Concepts and Architecture InnoDB 概念和结构体系: 14.2.1 MySQL and the ACID Model 14.2.2 InnoDB ...
- [MySQL Reference Manual]14 InnoDB存储引擎
14 InnoDB存储引擎 14 InnoDB存储引擎 14.1 InnoDB说明 14.1.1 InnoDB作为默认存储引擎 14.1.1.1 存储引擎的趋势 14.1.1.2 InnoDB变成默认 ...
- 学习笔记:The Best of MySQL Forum
http://mysql.rjweb.org/bestof.html I have tagged many of the better forum threads. 'Better' is based ...
- 温故而知新-MySQL高级编程
1 load data infile语句 MySQL下的命令 登录mysql命令行模式 load data infile "/var/www/1.txt" into table ...
- 没想到MySQL还会问这些...
前言 文本已收录至我的GitHub精选文章,欢迎Star:https://github.com/ZhongFuCheng3y/3y 在前一阵子,大哥问过我:"你知道MySQL的原子性是怎么保 ...
- (三)MySQL锁机制 + 事务
转: (三)MySQL锁机制 + 事务 表锁(偏读) 偏向MyISAM存储引擎.开销小,加锁快,无死锁,锁定粒度大,发生锁冲突的概率最高,并发最低. 查看当前数据库中表的上锁情况,0表示未上锁. sh ...
随机推荐
- Navicat连接阿里云服务器MSQL数据库
新买了台服务器Navicat老是连接不上数据库,查找一圈找到解决办法.So Easy 一.shell远程登录,进入数据库 mysql -uroot -p 二.输入以下命令进行授权: GRANT ALL ...
- Python自动化学习--元素定位
from selenium import webdriver import time driver = webdriver.Chrome() driver.get("https://www. ...
- wepy相关
1.根据官方文档: $ npm install @wepy/cli -g # 全局安装 WePY CLI 工具 $ wepy init standard myproj # 使用 standard 模板 ...
- Java开发神器——MyEclipse CI 2019.4.0 全新发布(附下载)
MyEclipse线上特惠,在线立享专属折扣!火热开启中>> MyEclipse 2019的升级版本中,推出对Java 11的支持.性能改进及新的连接器等. [MyEclipse CI 2 ...
- Mybatis(三)MyBatis 动态SQL
在 MyBatis 3 之前的版本中,使用动态 SQL 需要学习和了解非常多的标签,现在 MyBatis 采用了功能强大的 OGNL( Object-Graph Navigation Language ...
- linux-LVM磁盘扩容
查看磁盘 [ops@stock_kline_database ~]$ sudo fdisk -l 磁盘 /dev/sda: 字节, 个扇区 Units = 扇区 of * = bytes 扇区大小(逻 ...
- 【leetcode】K-th Symbol in Grammar
题目如下: 解题思路:直接把每行的数据计算出来肯定是不行的,因为N最大是30,那个第N行长度就是2^30次方,这显然不可取.那么就只能找规律了,我采取的是倒推法.例如假如我们要求出第四行第七个元素的值 ...
- FileUtils (从磁盘下载,从网络下载)
public class FileUtils { /** * realPath 磁盘路径 D://project/download/ * urlPath 后半部分路径 具体根据业务需求,例如:WEB- ...
- HTTP教程
适合人群 本教程已为计算机学科毕业生和Web开发人员准备,帮助他们了解与超文本传输协议(HTTP)相关的基本到高级概念. 预备知识 在继续本教程之前,最好对Web概念,Web浏览器,Web服务器, ...
- 算法题常见的BUG错误(总结)
1. 快排的partition if(l >= r) return ; int i = l, j = r; int tmp = v[i]; while(i < j) { while(i & ...