SQL SERVER的锁机制(四)——概述(各种事务隔离级别发生的影响)
六、各种事务隔离级别发生的影响
修改数据的用户会影响同时读取或修改相同数据的其他用户。即这些用户可以并发访问数据。如果数据存储系统没有并发控制,则用户可能会看到以下负面影响:
· 未提交的依赖关系(脏读)
· 不一致的分析(不可重复读)
· 幻读
(一)脏读:
例:张某正在执行某项业务,如下:
begin traninsert tbUnRead select 3,'张三'unionselect 4,'李四'---延迟秒,模拟真实交易情形,用于处理业务逻辑waitfor delay '00:00:05'rollback tran---此时李某对表中数据进行查询,执行了以下语句:set Transaction isolation level read uncommitted--查询数据select * from tbUnRead where name like '张%'
则李某可以看到张某所执行的插入语句,把数据添加到了数据库,如下图。
但是张某最终是没有提交事务,而是回滚了事务,所以这条记录并没有真正插入到数据库中。从而发生李某将脏读的数据当成真实的查询结果。
要解决此问题,就是要把数据库的事务隔离级别由未提交读修改成已提交读。只有当查询结果的正确性不是非常重要,或者是隔一段时间查询一次情况下,即使这一次查询结果是错,而下次查询结果是对的,并不会有太大影响,这才适合使用未提交读。
(二)不可重复读
例:张某正在查询数据,如下
set Transaction isolation level read committedbegin transelect * from tbUnRead where ID=2---延迟秒,模拟真实交易情形,用于处理业务逻辑waitfor delay '00:00:05'select * from tbUnRead where ID=2commit tran---此时李对表中数据进行了更新,如下语句:update tbUnReadset name='Jack_upd'where ID=2
上面的执行语句造成张某在同一个事务内,两次相同的查询条件,查询到不相同的结果(如下图)。
这是由于“已提交读”隔离级别对共享锁保留的时间是:一旦查询完毕就立即释放,而非事务完成才释放。所在张某虽然还在使用事务,事务过程中的所有独占锁都会一直保留,让事务中所更改的数据别人不可进行查询与更改,直到事务完成。但是,被查询的数据在事务过程中是查询完毕就立即释放共享锁,所以别人仍然可以进行修改,造成一笔事务中,两次相同的查询条件,可以得到不相同的结果。最佳的解决方案是将隔离级别设置为“可重复读”。
“可重复读”事务隔离级别,让事务过程中所曾经建立的共享锁都一直保留到事务完成,虽然可以避免“不可重复读”的问题,但是也会导致数据锁定太久,而别人无法读取数据,影响并发率,甚至提高了“死锁”的发生率。
(三)幻读
例:张某正在查询数据,如下
set Transaction isolation level REPEATABLE READbegin transelect * from tbUnRead where ID=3---延迟秒,模拟真实交易情形,用于处理业务逻辑waitfor delay '00:00:05'select * from tbUnRead where ID=3commit tran--此时李某新增了一条记录,如下语句:INSERT TBUNreadselect 3,'幻读'
张某已经把隔离级别设置为“可重复读”,虽然是曾经读取的数据,不管是共享锁还是互斥锁都 保留到了事务结束,但是无法阻止其他人运行新增操作,导致第一次查询时没有数据,第二次查询时却有了数据。被称为“幻读”。如下图。
为了避免此类问题,可以将隔离级别设置为“可序列化”,设置之后,则其他人则无法新增数据。
七、各隔离级别所能防止的访问错误
隔离级别 |
脏读 |
不可重复读 |
幻读 |
未提交读 |
是 |
是 |
是 |
已提交读 |
否 |
是 |
是 |
可重复读 |
否 |
否 |
是 |
快照 |
否 |
否 |
否 |
可序列化 |
否 |
否 |
否 |
八、常用锁与事务隔离级别间的交互影响
已提交读 |
可重复读 |
快照 |
可序列化 |
|
共享 |
读完数据后就释放 |
事务结束才释放 |
不加锁,以版本来控制 |
事务结束才释放 |
更新 |
读完数据后就释放或是升级成独占锁 |
读完数据后就释放或是升级成独占锁 |
不加锁,以版本来控制 |
读完数据后就释放或升级成独占锁 |
独占 |
事务结束才释放 |
事务结束才释放 |
不加锁,以版本来控制 |
事务结束才释放 |
九、动态锁定管理
数据库引擎使用动态锁定管理策略来控制锁定和系统的最佳成本效益。数据库引擎可以动态调整数据粒度与锁定类型,当使用最低一级的行锁而非更大范围的页锁时,可以降低两个事务要求相同范围的数据锁定的可能性,增强并行访问的能力,可同时服务更多的用户,减小死锁的机率。相反低级锁转为高级锁可以减小系统的资源负担,但会增加并行争用的可能性。
此机制由锁管理器进行管理,每一个锁都需要内存去记录,并且要与锁管理器进行合作,才能完成数据访问操作,你可以想像当表中有100万条记录时,你执行一条没有where语句的update指令时,在默认情况下数据库引擎会采用行锁,但这要记录100万条行锁记录,以及相关的意向共享锁,必定会消耗掉大量的系统资源,当系统资源不足时,数据库引擎会自动提升锁的级别,也就是由行锁提升为页锁,如果资源还是不足,则会再次提升,提升为表锁。
就以上例子来说,如果每个页可以放200条记录,则100万表记录的行锁转为5000个页锁,还省掉了大量的意向共享锁。如果资源还是一足,则可以再次提升锁级别,提升到表锁,这样就只需要一个锁就可以了。
愈大范围的锁花费在管理锁之上的资源就愈少。但相对来说,同时上线并发访问该资源的人数就越少。例如:或采用行锁,则你访问你的记录,我访问我的记录,互相不影响,但如果升级到页锁,则如果你先抢到该分页,而我要访问的记录又恰恰在这一分页上,则我必须要等你释放该分页之后才能访问。如果升级到表锁,则同一时间,该表中的记录只能一个人才能访问,其他人不能访问。如下图。
一般情况下,是不需要手工去设置锁定范围的,可以由Microsoft SQL Server 数据库引擎视情况而定,使用动态锁定策略确定最经济的锁。 执行查询时,数据库引擎会根据架构和查询的特点自动决定最合适的锁。 例如,为了缩减锁定的开销,优化器可能在执行索引扫描时在索引中选择页级锁。
动态锁定具有下列优点:
· 简化数据库管理。 数据库管理员不必调整锁升级阈值。
· 提高性能。 数据库引擎通过使用适合任务的锁使系统开销减至最小。
· 应用程序开发人员可以集中精力进行开发。 数据库引擎将自动调整锁定。
在 SQL Server 2008 中,锁升级的行为已发生改变,其中引入了 LOCK_ESCALATION选项
转载于:https://www.cnblogs.com/littlewrong/p/9025769.html
SQL SERVER的锁机制(四)——概述(各种事务隔离级别发生的影响)相关推荐
- 第八节:数据库层次的锁机制详解和事务隔离级别
一. 基本概念 1.共享锁:(holdlock) (1). select的时候会自动加上共享锁,该条语句执行完,共享锁立即释放,与事务是否提交没有关系. (2). 显式通过添加(holdlock)来显 ...
- SQL SERVER的锁机制(二)——概述(锁的兼容性与可以锁定的资源)
二.完整的锁兼容性矩阵(见下图) 对上图的是代码说明:见下图. 三.下表列出了数据库引擎可以锁定的资源. 名称 资源 缩写 编码 呈现锁定时,描述该资源的方式 说明 数据行 RID RID 9 文件编 ...
- 浅析如何掌握了解SQL Server的锁机制
各种大型数据库所采用的锁的基本理论是一致的,但在具体实现上各有差别.SQL Server更强调由系统来管理锁.在用户有SQL请求时,系统分析请求,自动在满足锁定条件和系统性能之间为数据库加上适当的锁, ...
- SQL Server数据库锁机制及类型
SQL Server数据库锁机制及类型 [06-05 12:08:14]作者:责任编辑:heyaorong Microsoft SQL Server(以下简称SQL Server)作为一种中小型数据库 ...
- SQL SERVER的锁机制(三)——概述(锁与事务隔离级别)
五.锁与事务隔离级别 事务隔离级别简单的说,就是当激活事务时,控制事务内因SQL语句产生的锁定需要保留多入,影响范围多大,以防止多人访问时,在事务内发生数据查询的错误.设置事务隔离级别将影响整条连接. ...
- SQL Server的锁机制
锁的概述 一. 为什么要引入锁 多个用户同时对数据库的并发操作时会带来以下数据不一致的问题: 丢失更新 A,B两个用户读同一数据并进行修改,其中一个用户的修改结果破坏了另一个修改的结果,比如订票系统 ...
- mysql 事物 锁行 测试_MySQL Transaction--RC事务隔离级别下加锁测试
##=========================================## 测试数据:CREATE TABLE`tb4001` ( `id`bigint(20) NOT NULLAUT ...
- mysql 事物 锁行 测试_MySQL Transaction--RR事务隔离级别下加锁测试
============================================================================== 按照非索引列更新 在可重复读的事务隔离级别 ...
- SQL锁机制和事务隔离级别
摘自:http://www.cnblogs.com/haiyang1985/archive/2009/02/27/1399641.html 锁机制 NOLOCK和READPAST的区别. 1. ...
最新文章
- 就算是戴上口罩,AI也知道你在说什么
- 利用JavaScript中的原型给对像添加方法
- 漫谈云计算与OpenStack的前世今生
- 分布式常见面试题总结(2021)
- Qt线程:QThread
- 无人车之美——论无人车辆系统的软件架构
- 如何通过树莓派/Python/smtp发送电子邮件
- Kali基于字典的无线破解
- 猫狗数据集百度网盘链接
- 中国水泥工业节能减排行业投资效益及未来发展战略规划报告2021-2027年
- 安装了PS2022 后,画笔工具使用延迟,操作卡到无法忍受,PS 插件合都卸载掉、设置暂存盘等方法都没有效果
- 书摘—做自己的公关专家
- 初探RxJava(基础篇)
- 计算机软件专业可以考哪些证书
- 现代信号处理——时频分析与时频分布(时频分布的基本理论)
- SSM和Springboot框架比较的优缺点
- php 如何生成noncestr,如何创建和使用nonce
- Booth理解与Booth改进版的由来
- 渣渣一记:)之HTML
- 开尔文夹接线图解_什么是开尔文四线检测|Kelvin Four-terminal sensing|开尔文|Kelvin 4|开尔文四线电阻检测-产品知识-资讯-深圳华壬电子...
热门文章
- java数据跑不出来,6000条数据,java下跑了20多分钟了还没跑完,求教怎么改进
- jenkins搭建_自动化测试系列之jenkins配置搭建环境
- 取代java_为什么C++没有被java取代
- 七阶拉丁方阵_最强大脑七阶立方之战规则解析 清华天才对其了如指掌
- linux设置静态IP及克隆后修改IP和hostname
- c语言af-1,单反对焦模式中的AF-S、AF-C、AF-A是什么意思,
- mysql myisam 去掉表锁a_MyISAM表锁的解决方案
- 和远程ip_【漏洞预警】Windows TCP/IP远程执行代码漏洞(CVE202016898)
- 计算机组成原理指令译码,计算机组成原理实验报告指令译码器.docx
- mysql一次性获取几十万数据_《快速念咒——MySQL自学入门指南》:第2章——从表中获取更多数据(前言)...