欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

SQL Server并发操作单个表时发生在page页面级的死锁

程序员文章站 2023-12-20 18:06:46
最近遇到的死锁问题都发生在并发操作单张表上,比较有意思,就模拟了重现了一下。根据非聚集索引为条件,删除某一个表的数据,类似于这么一个语句,delete from table where nocluster_index in (x,y,z,m,n……)in里面的内容不同,并发执行某些情况下,可能会引发 ......

 

最近遇到的死锁问题都发生在并发操作单张表上,比较有意思,就模拟了重现了一下。
根据非聚集索引为条件,删除某一个表的数据,类似于这么一个语句,delete from table where nocluster_index in (x,y,z,m,n……)in里面的内容不同,并发执行
某些情况下,可能会引发死锁,如下简单模拟重现一下这种情况。

 

如下用两张表来模拟上述场景:testpagelock代表要删除的表,testid来存储用来删除的id

SQL Server并发操作单个表时发生在page页面级的死锁

 

如下,用两个session即可,模拟并发,很快就会看到一条死锁的信息

SQL Server并发操作单个表时发生在page页面级的死锁

 

扩展事件ring_buffer target中中的死锁日志

SQL Server并发操作单个表时发生在page页面级的死锁

原理不难理解:
不同的session要删除的数据分布在不同的数据页面中,执行delete语句删除数据的情况下,也是一个查找然后加锁的过程
当要删除的数据落在不同的数据页面上的时候,一旦加锁顺序发生冲突,就会产生死锁
比如session1删除的数据分布在50,80,120页面上,session2删除的数据分布在100,120,140页面上,
session1和session2 要加锁的目标存在交集,一旦存在交集,并发情况就可能存在加锁顺序冲突,类似死锁因此而产生

 

解决:
最最简单暴力的就是显式锁提示,这里只能是tablockx;高级一点,遇到类似并发业务,可以使用队列进行排队。
估计会有人担心tablockx的性能问题会不会锁的太多了,测试发现直接显式tablockx锁提示,并不会非常大地影响性能,整体性能甚至会变高,
因为tablockx锁模式更加简单直接,会比行数需要的资源更少,因此在锁定资源上,处理起来比较高效。

 

上一篇:

下一篇: