MSSqlserver的锁模式介绍

一 SQL Server 锁类型的说明

在SQL Server数据库中加锁时,除了可以对不同的资源加锁,还可以使用不同程度的加锁方式,即有多种模式,SQL Server中锁模式包括:

1.共享锁(S) 共享锁用于所以的制度数据操作。共享锁是非独占的,允许多个并发事务读取其锁定的资源。默认情况下,数据被读取后,SQL Server立刻释放共享锁。

  例如: 执行查询"SELECT * FROM dbo.Customer"时,首先锁定第一页,读取之后,释放对第一页的锁定,然后锁定第二页。这样,就允许在读操作过程中,修改未被锁定的第一页。但是,事务隔离级别链接选项设置和SELECT语句中的锁定设置都可以改变SQL Server的这种默认设置。

    执行查询"SELECT * FROM dbo.Customer WITH(HOLDLOCK)"就要求在整个查询过程中,保持对表的锁定,直到查询完成才释放锁定。

2.更新锁(U) 更新锁在修改操作的初始化阶段用来锁定可能要被修改的资源,这样可以避免使用共享锁(S)造成的死锁现象。因为使用共享锁(S)时,修改数据的操作分为两步,首先获得一个共享锁(S),读取数据,然后再将共享锁升级为排它锁(X),然后执行修改操作。这样如果同时又两个或多个事务同时对一个事务申请共享锁,在修改数据的时候,这些事务将共享锁升级为排它锁(X)。这时,这些事务都不会释放共享锁而是一直等待对方释放,这样就造成了死锁。如果一个数据在修改前直接申请更新锁(U),在数据修改的时候再升级为排它锁(X),就可以避免死锁。

3.结构锁(Sch) 执行表的数据定义语言(DDL)操作(例如添加列或除去表)时使用架构修改(Sch-M)锁。当编译查询时,使用架构稳定性(Sch-S)锁。架构稳定性锁不阻塞任何事务锁,包括排它锁。因此在编译查询时,其它事务(包括在表上有排它锁的事务)都能继续运行。但不能在表上执行DDL操作。

4.意向锁(I) 意向锁说明SQL Server有在资源的底层获得共享锁或排它锁的意向。数据库引擎使用意向锁来保护共享锁或排它锁放置在锁层次结构的底层资源上。意向锁之所以命名为意向锁,是因为在较低级别锁前可获取它们,因此会通知意向将锁放置在较低级别上。

  例如:表级的共享意向锁说明事务意图讲排它锁释放在表中的页或者行。

     意向锁有可以分为:

      共享意向锁(IS):事务意图在共享意向锁所锁定的底层资源上放置共享锁来读取数据。

      排它意向锁(IX):事务意图在共享锁锁定的资源上放置排它锁来修改数据。

      共享式排它意向锁(SIX):事务允许其他事务使用共享锁来读取顶层资源,并意图在该资源低层上放置排它锁。

      意向锁的两种用途:

      • 防止其他事务以会使较低级别的锁无效的方式修改较高级别资源。
      • 提高数据库引擎在较高的粒度级别检测锁冲突的效率。          

5.大容量更新锁(BU) 当将数据大容量复制到表,且指定了TABLOCK提示或者使用sp_tableoption设置了table lock on bulk表选项时,将使用大容量更新锁。大容量更新锁允许进程将数据并发大容量复制到同一表,同时防止其它不进行大容量复制数据的进程访问该表。

SQL Server使用加锁功能说明:

  • NOLOCK(不加锁):SQL Server在读取数据时不加任何锁。在这种情况下,用户可能读取到未完成事务或者回滚中的数据,即所谓的“脏数据”。仅应用于SELECT语句。    
  • HOLDLOCK(保持锁): SQL Server会将此共享锁保持至整个事务结束,而不会再途中释放。也就是说,共享锁保留到事务完成,而不是在相应的表、行、或数据页不再需要时立即释放锁。等同于SERIALIZABLE。
  • PAGLOCK(页锁): 在通常使用单个表锁的地方采用页锁。READCOMMITTED用与运行在提交读隔离级别的事务相同的锁语义执行扫描。
  • READPAST:跳过锁定行,此选项导致事务跳过由其它事务锁定的行(这些行平常会显示在结果集内),而不是阻塞该事务,使其等待其它事务释放在这些行上的锁。仅用与SELECT语句。
  • READUNCOMMITTED: 等同于NOLOCK,用与运行在可重复读隔离级别的事务相同的锁语义执行扫描。
  • ROWLOCK:使用行级锁,而不适用粒度更粗的页级锁和表级锁。SERIALIZABLE用与运行在可串行读隔离级别的事务相同的锁语义执行扫描。等同于HOLDLOCK。
  • TABLOCK: 使用表锁代替粒度更细的行级锁或页级锁。在语句结束前,SQL Server一直持有该锁。但是,如果同时制定HOLDLOCK,那么在事务结束之前,锁将被一直持有。
  • UPDLOCK: 读取表时使用更新锁,而不使用共享锁,并将锁一直保留到语句或事务的结束。UPDLOCK的优点是允许您读取数据(不阻塞其它事务)并在以后更新数据,同时确保自从上次读取数据后数据没有被更改。
  • XLOCK: 使用排它锁并一直保持到语句处理的所有数据上的事务结束时。可以使用PAGLOCK或TABLOCK指定该锁,这种情况下排它锁适用于适当级别的粒度。至于锁定多少条记录的问题,sql默认的锁定行本来就是行级别锁定的,所以你用TOP 1指定只锁定一条记录就好。 SELECT TOP 1 * FROM dbo.Customer  WITH(UPLOCK,READPAST)

二 死锁与死锁解除

1. 死锁

  使用或管理数据库都不可避免的涉及到死锁,一旦发生死锁,数据相互等待对方资源的释放,会阻止对数据的访问,严重会造成DB挂掉,当资源被锁定,无法被访问时,可以终止访问DB的那个session来达到解锁的目的(即Kill掉造成锁的那个进程)。

  在两个或多个任务中,如果每个任务锁定了其它任务试图锁定的资源,此时会造成这些任务永久阻塞,从而出现死锁。例如:

    • 事务A 获取了行1的共享锁
    • 事务B获取了行2的共享锁
    • 现在,事务A请求行2的排它锁,但在事务B完成并释放其对行2的共享锁之前被阻塞。
    • 现在,事务B请求获取行1的排它锁,但在事务A完成并释放其行1持有的共享锁之前被阻塞。        

  事务B完成之后事务A才能完成,但是事务B由事务A阻塞。该条件也称为循环依赖关系:事务A依赖于事务B,事务B通过对事务A的依赖关系关闭循环。

  除非摸个外部进程断开死锁,否则死锁中的两个事务都将无线期等待下去。SQL Server数据库引擎死锁监视器定期检查陷入死锁的任务。如果监视器检测到循环依赖关系,将选择其中一个任务作为牺牲品,然后终止其事务并提示错误。这样,其它任务就可以完成其事务。对于事务以锁雾终止的应用程序,它还可以重试该事务,但通常要等到其它一起陷入死锁的其它事务完成后执行。

2. 死锁检测

  • SQL Server数据库引擎自动检测SQL Server中的死锁循环。数据库引擎选择一个会话作为死锁牺牲品,然后终止当前事务来打断死锁。
  • 查看DMV:sys.dm_tran_locks (SELECT resource_type,resource_description,resource_associated_entity_id,request_mode,request_status,request_owner_type FROM sys.dm_tran_locks WHERE resource_type!=‘DATABASE‘)  
  • SQL Server Profile能够直观的显示死锁的图形事件。

  

  死锁示例:

    第一个连接中执行:

    

BEGIN TRAN
UPDATE dbo.Customer SET NRIC=‘1000‘ WHERE TransactionNumber=6
WAITFOR DELAY ‘00:00:30‘
UPDATE dbo.Employee SET ts=1111 WHERE TransactionNumber=1
COMMIT

    第二个连接中执行

BEGIN TRAN
UPDATE dbo.Employee SET ts=1111 WHERE TransactionNumber=1
WAITFOR DELAY ‘00:00:10‘
UPDATE dbo.Customer SET NRIC=‘1000‘ WHERE TransactionNumber=6

COMMIT

  如果两个连接同时执行数据库(SQL Server2008)会自动检测到死锁,终止其中一个进程。

原文地址:https://www.cnblogs.com/wangjunqiao/p/9532071.html

时间: 2024-08-04 08:50:31

MSSqlserver的锁模式介绍的相关文章

SQL 锁的介绍

锁的概述 一. 为什么要引入锁 多个用户同时对数据库的并发操作时会带来以下数据不一致的问题: 丢失更新A,B两个用户读同一数据并进行修改,其中一个用户的修改结果破坏了另一个修改的结果,比如订票系统 脏读A用户修改了数据,随后B用户又读出该数据,但A用户因为某些原因取消了对数据的修改,数据恢复原值,此时B得到的数据就与数据库内的数据产生了不一致 不可重复读A用户读取数据,随后B用户读出该数据并修改,此时A用户再读取数据时发现前后两次的值不一致 并发控制的主要方法是封锁,锁就是在一段时间内禁止用户做

Windows7中7种不同关机模式介绍

在Win7关机选项中一共有7种关闭方式,分别为 Switch user(切换用户), Log off(登出), Lock(锁定), Restart(重启), Sleep(睡眠), Hibernate(休眠), Shut down(关机). 下面分别介绍一下它们的区别: 1.Switch user, Log off, Lock Win7支持多用户登录.也就是说,用户可以以管理员或是其他用户身份同时登录.如下图:在我的系统中目前有两个用户在登陆,一个处于Active(活动)状态,一个处于Discon

无锁模式的Vector

这两天学习无锁的并发模式,发现相比于传统的 同步加锁相比,有两点好处1.无锁 模式 相比于 传统的 同步加锁  提高了性能 2.无锁模式 是天然的死锁免疫 下来介绍无锁的Vector--- LockFreeVector 它的结构是: private final AtomicReferenceArray<AtomicReferenceArray<E>> buckets; 从这里我们可以看到,它的内部是采用的是 无锁的引用数组, 数组嵌套数组 相当于一个二维数组,它的大小可以动态的进行

oracle 锁的介绍 (转)

本文转自:http://blog.csdn.net/gyb2013/article/details/6929697 一.什么是锁: Oracle的锁机制是一种轻量级的锁定机制,不是通过构建锁列表来进行数据的锁定管理,而是直接将锁作为数据块的属性,存储在数据块首部.这个是通过ITL来实现的,一个事务要修改块中的数据,必须获得该块中的一个itl.关于itl(事务槽)的介绍可参考http://blog.csdn.net/gybyylx/article/details/6893639. 说明:在orac

Java 中15种锁的介绍:公平锁,可重入锁,独享锁,互斥锁,乐观锁,分段锁,自旋锁等等(转)

Java 中15种锁的介绍 在读很多并发文章中,会提及各种各样锁如公平锁,乐观锁等等,这篇文章介绍各种锁的分类.介绍的内容如下: 公平锁 / 非公平锁 可重入锁 / 不可重入锁 独享锁 / 共享锁 互斥锁 / 读写锁 乐观锁 / 悲观锁 分段锁 偏向锁 / 轻量级锁 / 重量级锁 自旋锁 上面是很多锁的名词,这些分类并不是全是指锁的状态,有的指锁的特性,有的指锁的设计,下面总结的内容是对每个锁的名词进行一定的解释. 公平锁 / 非公平锁 公平锁 公平锁是指多个线程按照申请锁的顺序来获取锁. 非公

AQS详解之独占锁模式

AQS介绍 AbstractQueuedSynchronizer简称AQS,即队列同步器.它是JUC包下面的核心组件,它的主要使用方式是继承,子类通过继承AQS,并实现它的抽象方法来管理同步状态,它分为独占锁和共享锁.很多同步组件都是基于它来实现的,比如我门常见的ReentrantLock,它是基于AQS的独占锁实现的,它表示每次只能有一个线程持有锁.在比如ReentrantReadWriteLock它是基于AQS的共享锁实现的,它允许多个线程同时获取锁,并发的访问资源.AQS是建立在CAS上的

忙信号模式介绍

在阅读本文前,您需要了解云计算与互联网开发基础知识.[忙信号模式]是专注应用程序对当云服务请求响应不成功时忙信号如何处理.这种模式从客户端角度出发,这里主要描述的云计算中场景.客户端是每发出请求到服务端,服务端答复忙信号.客户端负责根据忙信号做出适当数量的重试次数处理.如果重试过程中继续收到忙信号,客户端将该服务视为不可用.我们偶尔地拨号电话结果是忙信号,正常的反应需要重拨,这时通常会导致能成功建立通话. 同样,偶尔会调用服务结果被返回失败代码,表明云服务目前不能够满足该请求.需要重试,在服务端

CDN模式介绍

CDN(content delivery network 或 content distribution network)模式专注于通过全球分布式缓存架构为经常访问的文件减少网络访问时的延迟.目标是加快交付应用程序内容给用户.内容是任何可以存储在一个文件,如图像. 视频和文档.内容交付网络 (CDN) 是一种全球分布式缓存的服务.CDN 在世界各地的许多地方保存了应用程序文件的副本.当用户访问时,会选择离这些地方接近结点,内容不需要走长距离网络来传递,所以它能访问到达速度更快,以此来改善用户体验.

SqlServer 并发事务(二):锁粒度和锁模式

锁粒度: 资源 格式 说明 DATABASE 不适用 resource_database_id 列中已提供数据库 ID. FILE <file_id> 此资源所表示的文件 ID. Object <object_id> 此资源所表示的对象 ID. 此对象可以是sys.objects 中列出的任何对象,不仅仅是表. PAGE <file_id>:<page_in_file> HoBt ID.此值与 sys.partitions.hobt_id 相对应. PAGE