当前位置: 首页 > 编程日记 > 正文

T-SQL笔记3:事务、锁定和并发

T-SQL笔记3:事务、锁定和并发

本章摘要

1:事务

1.1:显式事务

1.2:使用DBCC OPENTRAN显示最早的活动事务

2:锁定

2.1:查看锁的活动

3:并发影响及隔离级别

3.1:并发影响

3.2:隔离级别

4:阻塞

4.1:找到并解决阻塞进程

4.2:设定阻塞时间

5:死锁

1:事务

事务是单个的工作单元。如果某一事务成功,则在该事务中进行的所有数据修改均会提交,成为数据库中的永久组成部分。如果事务遇到错误且必须取消或回滚,则所有数据修改均被清除。SQL Server 以下列事务模式运行。

自动提交事务:每条单独的语句都是一个事务。

显式事务:每个事务均以 BEGIN TRANSACTION 语句显式开始,以 COMMIT 或 ROLLBACK 语句显式结束。(是最推荐使用的模式)

隐式事务:在前一个事务完成时新事务隐式启动,但每个事务仍以 COMMIT 或 ROLLBACK 语句显式完成。(一般不建议使用)

1.1:显式事务

显式事务命令如下:

BEGIN TRANSACTION:设置一个显式事务的起点。

ROLLBACK TRANSACTION:恢复由一个事务修改的原始数据,使数据回到事务开始时的状态,并释放事务占据的资源。

COMMIT TRANSACTION:如果没有遇到错误则结束事务并永久实现修改,并释放事务占据的资源。

BEGIN DISTRIBUTED TRANSACTION:分布式事务起点。

SAVE TRANSACTION:在事务内部设置一个保存点,允许我们定义一个事务取消后能返回的位置。

@@TRANCOUNT:返回连接的活动事务数量。BEGIN TRANSACTION将@@TRANCOUNT加1,ROLLBACK TRANSACTION和COMMIT TRANSACTION将@@TRANCOUNT减1。

1.2:使用DBCC OPENTRAN显示最早的活动事务

如果在指定数据库内存在最早的活动事务和最早的分布式和非分布式复制事务,则显示与之有关的信息。

DBCC OPENTRAN [         ( [ database_name | database_id | 0 ] ) ]     { [ WITH TABLERESULTS ]       [ , [ NO_INFOMSGS ] ]     } ]

2:锁定

当多个用户或应用程序同时访问同一数据时,锁定可防止这些用户或应用程序同时对数据进行更改。

在较小粒度(如行级)上锁定会提高并发性,但是如果锁定许多行,则必须持有更多的锁。在较大粒度(如表级)上锁定会降低并发性,因为锁定整个表会限制其他事务对该表任何部分的访问。但是,在表级锁定中,持有的锁较少。

默认情况下,SQL Server Compact Edition 对数据页使用行级锁定,对索引页使用页级锁定。

下表显示了 SQL Server Compact Edition 可以锁定的资源:

RID:行标识符。用于锁定表内的单个行。

PAG:数据页或索引页。

TAB:整个表,包括所有数据和索引

MD:表的元数据。用于保护表架构

DB:数据库

下表显示了数据库引擎使用的资源锁模式:

共享 (S):用于不更改或不更新数据的读取操作,如 SELECT 语句。

更新 (U):用于可更新的资源中。防止当多个会话在读取、锁定以及随后可能进行的资源更新时发生常见形式的死锁。

排他 (X):用于数据修改操作,例如 INSERT、UPDATE 或 DELETE。确保不会同时对同一资源进行多重更新。

意向:用于建立锁的层次结构。意向锁包含三种类型:意向共享 (IS)、意向排他 (IX) 和意向排他共享 (SIX)。

架构:在执行依赖于表架构的操作时使用。架构锁包含两种类型:架构修改 (Sch-M) 和架构稳定性 (Sch-S)。

大容量更新 (BU):在向表进行大容量数据复制且指定了 TABLOCK 提示时使用。

键范围:当使用可序列化事务隔离级别时保护查询读取的行的范围。确保再次运行查询时其他事务无法插入符合可序列化事务的查询的行。

2.1:查看锁的活动

示例:

新建一个查询编辑器,键入并运行:

BEGIN TRAN
SELECT ProductID, DocumentID, ModifiedDate
FROM Production.ProductDocument
WITH(TABLOCKX)

打开第二个查询编辑器,键入并运行:

SELECT request_session_id sessionid,
    resource_type type,
    resource_database_id dbid,
    OBJECT_NAME(resource_associated_entity_id) objectname,
    request_mode rmode,
    request_status rstatus
FROM sys.dm_tran_locks

得到结果:

{@WXX5UOK2RN_E_DNF109(7

在这个示例中,首先启动一个新的事务,并使用TABLOCKX对表放置了排它锁。第二个查询编辑器中运行的就是查看该数据库中活动锁的列表。第三行就是在ProductDocument上的排它锁。

3:并发影响及隔离级别

3.1:并发影响

并发影响所产生的影响主要有以下四类:

丢失更新

当两个或多个事务选择同一行,然后基于最初选定的值更新该行时,会发生丢失更新问题。每个事务都不知道其他事务的存在。最后的更新将覆盖由其他事务所做的更新,这将导致数据丢失。

例如,两个编辑人员制作了同一文档的电子副本。每个编辑人员独立地更改其副本,然后保存更改后的副本,这样就覆盖了原始文档。最后保存其更改副本的编辑人员覆盖另一个编辑人员所做的更改。如果在一个编辑人员完成并提交事务之前,另一个编辑人员不能访问同一文件,则可避免此问题。

未提交的依赖关系(脏读)

当第二个事务选择其他事务正在更新的行时,会发生未提交的依赖关系问题。第二个事务正在读取的数据还没有提交并且可能由更新此行的事务所更改。

例如,一个编辑人员正在更改电子文档。在更改过程中,另一个编辑人员复制了该文档(该副本包含到目前为止所做的全部更改)并将其分发给预期的用户。此后,第一个编辑人员认为目前所做的更改是错误的,于是删除了所做的编辑并保存了文档。分发给用户的文档包含不再存在的编辑内容,并且这些编辑内容应视为从未存在过。如果在第一个编辑人员保存最终更改并提交事务之前,任何人都不能读取更改的文档,则可以避免此问题。

不一致的分析(不可重复读)

当第二个事务多次访问同一行而且每次读取不同的数据时,会发生不一致的分析问题。不一致的分析与未提交的依赖关系类似,因为其他事务也是正在更改第二个事务正在读取的数据。但是,在不一致的分析中,第二个事务读取的数据是由已进行了更改的事务提交的。此外,不一致的分析涉及多次(两次或更多)读取同一行,而且每次信息都被其他事务更改,因此我们称之为“不可重复读”。

例如,编辑人员两次读取同一文档,但在两次读取之间,作者重写了该文档。当编辑人员第二次读取文档时,文档已更改。原始读取不可重复。如果在编辑人员完成最后一次读取文档之前,作者不能更改文档,则可以避免此问题。

幻读

当对某行执行插入或删除操作,而该行属于某个事务正在读取的行的范围时,会发生幻读问题。由于其他事务的删除操作,事务第一次读取的行的范围显示有一行不再存在于第二次或后续读取内容中。同样,由于其他事务的插入操作,事务第二次或后续读取的内容显示有一行并不存在于原始读取内容中。

例如,一个编辑人员更改作者提交的文档,但当生产部门将其更改内容合并到该文档的主副本时,发现作者已将未编辑的新材料添加到该文档中。与不可重复读的情况相似,如果在编辑人员和生产部门完成对原始文档的处理之前,任何人都不能将新材料添加到文档中,则可以避免此问题。

3.2:隔离级别

ISO 标准定义了下列隔离级别,SQL Server 数据库引擎支持所有这些隔离级别:

  • 未提交读(READ UNCOMMITTED)(隔离事务的最低级别,只能保证不读取物理上损坏的数据)
  • 已提交读(READ COMMITTED)(数据库引擎的默认级别)
  • 可重复读(REPEATABLE READ)
  • 可序列化(SERIALIZABLE)(隔离事务的最高级别,事务之间完全隔离)
  • 快照(SNAPSHOT)

下表显示了不同隔离级别导致的并发副作用。

隔离级别      脏读 不可重复读 幻读

未提交读       是   是            是

已提交读       否   是            是

可重复读       否   否            是

快照              否   否            否

可序列化       否   否            否

使用SET TRANSACTION ISOLATION LEVEL { | }可以设置隔离级别。

4:阻塞

首先罗列一些发生阻塞的原因:

a、如果没有适当索引,阻塞问题会加剧。在一个没有索引的表上的过量的行锁会导致SQL SERVER得到一个表锁,从而阻塞其它事务。

b、应用程序打开一个事务后,保持事务打开,然后要求用户进行反馈或者交互。通常是让最终用户在GUI上输入数据而保持事务打开的时候发生。保持打开的话,任何事务引用的资源会被锁占据。

c、事务BEGIN后查询的数据可能在事务开始之前被引用。

d、查询不适当地使用锁提示。例如,应用程序仅使用很少的行,但却使用了一个表锁提示。

e、应用程序使用长时间运行的事务,在一个事务中更新了很多行或很多表(把大量更新的事务变成较小更新的事务能帮助改善并发性)。

4.1:找到并解决阻塞进程

以一个示例来阐述此问题:

在第一个查询编辑器中运行下列代码来创建一个阻塞的进程:

BEGIN TRAN
UPDATE Production.ProductInventory
SET Quantity=406
WHERE ProductID=1 AND LocationID=1

在第二个查询编辑器中运行下列代码来创建一个阻塞的进程:

BEGIN TRAN
UPDATE Production.ProductInventory
SET Quantity=400
WHERE ProductID=1 AND LocationID=1

发现第二个编辑器中的命令永远不成功。这是因为第一个连接的事务永不提交,第二个连接只能无限期排队。

在第三个查询编辑器中运行:

SELECT blocking_session_id, wait_duration_ms, session_id
FROM sys.dm_os_waiting_tasks
WHERE blocking_session_id IS NOT NULL

这个时候,可以查到被阻滞的线程:

image

调用命令:

KILL 54

完成杀掉阻塞进行,可以看到第二个编辑器中的命令已经执行成功了。

4.2:设定阻塞时间

可以通过使用SET LOCK_TIMEOUT timearg来设定阻塞时间。

5:死锁

首先模拟一个死锁。

在第一个窗口运行:

SET NOCOUNT ON
SET TRANSACTION ISOLATION LEVEL SERIALIZABLE

WHILE 1=1
BEGIN
BEGIN TRAN
    UPDATE Purchasing.Vendor
    SET CreditRating=1
    WHERE VendorID=2
    UPDATE Purchasing.Vendor
    SET CreditRating=2
    WHERE VendorID=1
COMMIT TRAN
END

在第二个窗口运行:

SET NOCOUNT ON
SET TRANSACTION ISOLATION LEVEL SERIALIZABLE

WHILE 1=1
BEGIN
BEGIN TRAN
    UPDATE Purchasing.Vendor
    SET CreditRating=2
    WHERE VendorID=1
    UPDATE Purchasing.Vendor
    SET CreditRating=1
    WHERE VendorID=2
COMMIT TRAN
END

运行几秒钟后,检查两个窗口,其中一个窗口会出现:

Transaction (Process ID 52) was deadlocked on lock resources with another process and has been chosen as the deadlock victim. Rerun the transaction.

在第三个窗口中运行:

DBCC TRACEON(1222, -1)
GO
DBCC TRACESTATUS

使用1222标志位,将会在日志中记录被锁资源和类型的信息。这样我们就能分析出错的地方,找到解决方案。

TMJ .NET培训,开创 200元/月,学到会!
NET C# 入门级.NET C# 专业级.NET 架构级BS系统专业级BS系统安全
1.开篇及C#程序、解决方案的结构
2.源码管理之TFS入门
3.打老鼠初级
……
21.CMS之主要功能实现
22.进程和线程基础
23.类型转换
24.算法基础
25.初级课程之剩余知识点
1.消灭打老鼠游戏中的自定义委托
2.垃圾回收
3.Dispose模式
……
16.异常使用指导
17.最常用的重构指导
18.Debug和IDE的进阶
19.Resharper的使用
20.ILSPY的使用
1.Socket入门
2.打造打老鼠游戏网络版
3.WCF入门
……
10.依赖注入
11.万物兼可测试
12.软件指标之覆盖率计算
13.软件指标之代码行
14.软件指标之圈复杂度、嵌套深度
1.HTML
2.WebForm原理
3.CSS必知必会
……
19.让浏览器缓存Shop
20.Asp.net的生命周期
21.Asp.net网站的发布以及调试晋级
22.BS程序的本质
23.压力测试我们的Shop
1.Fiddler必知必会
2.IE开发者工具必知必会
3.跨站脚本防范
4.权限欺骗防范
5.参数越界防范
6.会话劫持防范
7.CSRF防范
8.盗链防范
9.静态文件的保护


将本文分享到: QQ空间 新浪微博 人人网 开心网 搜狐微博 MSN 谷歌 更多

转载于:https://www.cnblogs.com/luminji/archive/2010/10/12/1848986.html

相关文章:

几种常用数据库比较

目前,商品化的数据库管理系统以关系型数据库为主导产品,技术比较成熟。面向对象的数据库管理系统虽然技术先进,数据库易于开发、维护,但尚未有成熟的产品。国际国内的主导关系型数据库管理系统有Oracle、Sybase、INFORMIX和INGRES…

成功将BlogEngine 1.5 升级到了BlogEngine 2.0

使用BlogEngine.Net博客系统有两年时间了。官方的最新版本已经出到了2.5。但它是基于.net4.0的。也就是说服务器必须安装.net4.0,运行环境必须选择4.0。出于移植性的考虑。我决定将我的博客升级到2.0。BlogEngine.Net2.0是继续.net2.0的。虽说必须安装.net 3.5&…

【java】4.27上课及做作业时遇到的问题及第十六节课笔记整理

注意: 部分知识点只在eclipse运行环境中适用 1、字符串转化为字符数组的方法: 代码实现: char[] strcs text.toCharArray();2、字符数字转化为字符串 String reStr new String(re,0 ,position);3、打包及 引包的方法 (1) 用ex…

【Android】基于A星寻路算法的简单迷宫应用

简介 基于【漫画算法-小灰的算法之旅】上的A星寻路算法,开发的一个Demo。目前实现后退、重新载入、路径提示、地图刷新等功能。没有做太多的性能优化,算是深化对A星寻路算法的理解。 界面预览: 初始化: 寻路: 后退: 提示: 完成: 刷新地图: 下载地址: 项目…

[转]SQL 约束讲解

约束主要包括: •NOT NULL •UNIQUE •PRIMARY KEY •FOREIGN KEY •CHECK •DEFAULT 1、not null :用于控制字段的内容一定不能为空(NULL)。 用法 :Create table MyTable ( id …

JSON 转 VO

需求 将获取的json数据直接转为vo 解决 利用net.sf.json.JSONObject的toBean() 确保json中的key值和vo中的字段名称一致 JSONObject jsonObject new JSONObject();UserVO vo new UserVO(); vo (UserVO) net.sf.json.JSONObject.toBean(jsonObject, UserVO.class);参考文档地…

怎样查看一个端口有无开启

有时候我们需要确定一下某个端口有无开启,有两种方法。 方法 1:查看一个端口有无开启的最简单方法 查看端口有无开启,需要在dos里使用命令来完成。这个命令就是: netstat -ano这个命令能显示当前电脑有哪些端口正在使用&#xff0…

一道SQL统计试题

根据上图A表和B表,按照年份和地区生成1至12个月的数据,结果如下: 方法一: select YEAR,AreaName, MAX(case Month when 1 then Money else 0 end) as [1月], MAX(case Month when 2 then Money else 0 end) as [2月], MAX(case Mo…

【单片机】时钟周期 器械周期 指令周期的关系

1、 时钟周期(振荡周期):始终周期也称振荡周期,定义为时钟频率的倒数。时钟周期是计算机中最基本的、最小的单位。在一个始终周期内,CPU仅完成一个最基本的动作。时钟周期是一个时间的量。始终周期表示了SDRAM&#xf…

Painting A Board --POJ 1691

1、题目类型:暴力法、DFS。 2、解题思路:题意,一块大的矩形区域的被分成多个矩形区域,现在要给不同的区域涂上不同的颜色,有不同颜色的刷子可以提供,每个刷子可以刷一种不同的颜色。每刷一次,将…

《JavaScript高级程序设计》读书笔记【一】

JavaScript介绍 ECMAScript,由ECMA-262定义,提供核心语言功能;  文档对象模型(DOM),提供访问和操作网页内容的方法和接口;  浏览器对象模型(BOM),提供与浏…

上不了名校?可以在 GitHub 上读他们的课程

今天开始,全国各大区域的高考成绩陆续公布,又到了几家欢喜几家愁的时刻,如果你准备报考计算机相关专业,但是又由于分数不高而苦恼。别担心,在 GitHub 上有着大量的名校教学资源,即使上不了名校,…

【java】各种方法的使用(不定期更新)

疑难杂症篇 1、输入一个字符的方法 问题在于Scanner中没有一个类似于nextInt()之类的函数。 代码实现 char num scanner.next().charAt(0);2、将字符串转化为数字 没啥问题就是记不下来 代码实现: int a1 Integer.parseInt(i1);3、字符串转化为字符数组的方法 …

SQL SERVER 触发器示例

触发器是一种特殊的存储过程。 触发器语法 : CREATE TRIGGER trigger_name ON { table | view } [ WITH ENCRYPTION ] { FOR | AFTER | INSTEAD OF } { [ INSERT ] [ DELETE ] [ UPDATE ] } [ WITH APPEND ] [ NOT FOR REPLICATION ] AS sql_statement [ ...n ] 示…

vc数据库知识

在连接SQL数据库时,数据库的链接: _bstr_t strConn"ProviderSQLOLEDB.1;Data Source.;Initial Catalogdb_test;Integrated SecuritySSPI;Persist Security InfoFalse"; _ConnectionPtr m_pConnection; m_pConnection.CreateInstance(__uuidof(connection)…

jmeter 测试 api 接口方法

双击 “jmeter.bat” 打开 Jmeter 页面,如下图所示。 右击“测试计划”,添加 -> Theaders(Users) -> 线程组 在线程组中可以设置线程数、并发数、循环数等。 下面开始进行几种 jmeter 的接口测试方法。 1、get 请求配置 右击…

我要学ASP.NET MVC 3.0(一): MVC 3.0 的新特性

摘要 MVC经过其1.0和2.0版本的发展,现在已经到了3.0的领军时代,随着技术的不断改进,MVC也越来越成熟。使开发也变得简洁人性化艺术化。 园子里有很多大鸟都对MVC了如指掌,面对问题犹同孙悟空的七十二变一般游刃有余,令…

【java】兴唐第12-14节笔记整理

第十四节课 1、eclipse快捷键 alt shift s给所有属性写get set函数 2、给文件重命名: ctrl F2 3、上转型对象调用方法调用的是子类重写的方法 4、在任何情况下,子类对象都可以访问父类受保护方法(protected) 注意: …

[ZZ]Map/Reduce hadoop 细节

转自:Venus神庙原文:http://www.cnblogs.com/duguguiyu/archive/2009/02/28/1400278.html 分布式计算(Map/Reduce) 分布式计算,同样是一个宽泛的概念,在这里,它狭义的指代,按Google …

类加载器双亲委派模式

双亲委派模型的工作流程是:如果一个类加载器收到了类加载的请求,它首先不会自己去尝试加载这个类,而是把请求委托给父加载器去完成,依次向上,因此,所有的类加载请求最终都应该被传递到顶层的启动类加载器中…

Kubernetes 架构(下)【转】

上一节我们讨论了 Kubernetes 架构 Master 上运行的服务,本节讨论 Node 节点。 Node 是 Pod 运行的地方,Kubernetes 支持 Docker、rkt 等容器 Runtime。 Node上运行的 Kubernetes 组件有 kubelet、kube-proxy 和 Pod 网络(例如 flannel&#…

【工具软件】Xmind的使用

1、打开历史保存的记录的方法 窗口 - 文本编辑历史 - 恢复 2、批量修改 编辑 - 查找/替换 3、如果子主体很多,而且有文本格式的,可以直接选中父父主题复制粘贴 4、窗口 - 黑匣子 自己做的脑图系统会自动备份。 5、常用快捷键 (1)创建子主…

小脚本,统计一个目录下满足特定条件文件的代码行数

find -regex .*cc -o -regex .*h | xargs wc -lfind也自带了执行命令的方法:find -regex .*cc -o -regex .*h -exec wc -l {} \; 这种方法的结果不太对,只能统计到满足 -regex .*h 的文件注明一下: find默认从当前目录递归的查找&#xff1b…

CCNA CCNP CCIE所有实验名称完整版

只能仅供参考了!具体的实验内容就没了,失望了!实验1:通过Console端口访问Cisco路由器  实验2:通过Telnet访问Cisco路由器  实验3:配置终端服务器  实验4:通过浏览器访问路由器  实验5&#…

Real World Haskell 第七章 I/O

几乎所有程序都是用来从外部世界收集数据,处理数据,并把处理结果返回给外部世界的。也就是说,输入和输出对于程序设计来说相当关键。Haskell的I/O系统很强大,表达能力很强也很容易使用,理解它的原理对于学习Haskell来说…

malloc函数分配失败处理的严重性

本次在实际测试情况下,发现程序无缘无故的异常,导致看门狗超时复位,经过排查是malloc函数分配失败的时候,依然对指针进行了操作,导致异常。以前没重视这个问题是因为,总觉的malloc基本都会成功的&#xff0…

kvm--virsh命令行下管理虚拟机

virsh 既有命令行模式,也有交互模式,在命令行直接输入 virsh 就进入交互模式, virsh 后面跟命令参数,则是命令行模式; (1)基础操作 --- 命令行下管理虚拟机 virsh list 列出当前宿…

【java】兴唐第十八节课

1、java接口的关键字:implements,可实现多个接口,接口接口之间使用逗号分隔。 注: 继承只能继承一个,接口可以实现多个 2、在接口里所有的方法都是抽象方法,不用关键字abstract修饰。 3、接口不能定义变量&#xff0…

转换前台javascript传递过来的时间字符串到.net的DateTime

javascript: var datenew Date().toString();得到的结果类似于:Wed Oct 27 2010 08:53:04 GMT0800 如何在C#中把这个字符串转换为DateTime类型呢?DateTime.ParseExact("Wed Oct 27 16:23:44 UTC0800 2010","ddd MMM dd HH:mm:ss UTCzzzzz yyyy"…

树状数组 | 1057

用哈希,把push的数x作为下标给hashTable(实则不存在,直接用tree树状数组记录数据)1,pop则是以最后一个数x作为下标-1 。 树状数组和其原理不再赘述,需要注意的是最后的二分搜索(实则是lower_bou…