SQLServer中,大表的数据删除操纵,单次删除和批量多次删除产生的事件日记 ...

打印 上一主题 下一主题

主题 1660|帖子 1660|积分 4980

 
1,应用场景

SQLServer中一个大表(测试环境万万级,实际环境下会更多,达到10亿级),删除此中大部分数据。然后测试分批多次删除和一次性全部删除产生的transaction log的日记巨细的问题。另:受限于相干的表做了复制分发,因此无法通过备份部分数据后truncate table的方式来实现,也无法通过新建一个表,通过rename的方式来交换实现,这两种方式不再考虑范围之内,也不是本文的重点。  以下为天生测试数据库前置条件:1,数据库为SQLServer 2019标准版2,测试文件所在的磁盘为普通普通SSD(非NVME类型SSD)3,创建两个一样的数据库,保持数据库的初始巨细,增长巨细,日记的初始巨细,增长巨细,两个数据库均为full recovery模式4,两个库中界说完全一样的表,写入完全划一的测试数据,最低1000W起步,否则测试意义不大 以下为测试脚本
  1. USE [master]
  2. GO
  3. CREATE DATABASE [TransactionTest_01] ON PRIMARY
  4. ( NAME = N'TransactionTest_01_Data', FILENAME = N'D:\MSSQL\Data\TransactionTest_01.mdf' , SIZE = 32768KB , MAXSIZE = UNLIMITED, FILEGROWTH = 32768KB)
  5. LOG ON
  6. ( NAME = N'TransactionTest_01_Log', FILENAME = N'D:\MSSQL\Log\TransactionTest_01_Log.ldf' , SIZE = 65536KB , MAXSIZE = UNLIMITED, FILEGROWTH = 131072KB )
  7. GO
  8. USE [master]
  9. GO
  10. CREATE DATABASE [TransactionTest_02] ON PRIMARY
  11. ( NAME = N'TransactionTest_02_Data', FILENAME = N'D:\MSSQL\Data\TransactionTest_02.mdf' , SIZE = 32768KB , MAXSIZE = UNLIMITED, FILEGROWTH = 32768KB)
  12. LOG ON
  13. ( NAME = N'TransactionTest_02_Log', FILENAME = N'D:\MSSQL\Log\TransactionTest_02_Log.ldf' , SIZE = 65536KB , MAXSIZE = UNLIMITED, FILEGROWTH = 131072KB )
  14. GO
  15. use [TransactionTest_01]
  16. go
  17. create table test01
  18. (
  19.     c1 int identity(1,1),
  20.     c2 varchar(100),
  21.     c3 varchar(100),
  22.     c4 varchar(100),
  23.     c5 varchar(100),
  24.     c6 varchar(100),
  25.     c7 varchar(100),
  26.     c8 varchar(100),
  27.     c9 varchar(100),
  28.     c10 datetime2,
  29.     constraint pk_test01 primary key(c1)
  30. );
  31. use [TransactionTest_02]
  32. go
  33. create table test01
  34. (
  35.     c1 int identity(1,1),
  36.     c2 varchar(100),
  37.     c3 varchar(100),
  38.     c4 varchar(100),
  39.     c5 varchar(100),
  40.     c6 varchar(100),
  41.     c7 varchar(100),
  42.     c8 varchar(100),
  43.     c9 varchar(100),
  44.     c10 datetime2,
  45.     constraint pk_test01 primary key(c1)
  46. );
  47. go
  48. --生成测试数据,这里是5千万,如果磁盘太慢或者其他原因,可以减小@i参数的值,少生成一些数据
  49. declare @i int = 0
  50. begin tran;
  51. while @i<50000000
  52. begin
  53.     declare @var varchar(100) = newid();
  54.     declare @currentdatetime datetime2 = sysdatetime();
  55.     insert into TransactionTest_01..test01 values (@var,@var,@var,@var,@var,@var,@var,@var,@currentdatetime);
  56.     insert into TransactionTest_02..test01 values (@var,@var,@var,@var,@var,@var,@var,@var,@currentdatetime);
  57.    
  58.     set @i = @i + 1;
  59.     if @i%10000=0
  60.     begin
  61.         commit;
  62.         begin tran;
  63.     end
  64. end
  65. if @@trancount > 0
  66.     commit;
  67. go
  68. --验证数据的一致性
  69. select count(1) from TransactionTest_01..test01 with(nolock);
  70. select count(1) from TransactionTest_02..test01 with(nolock);
  71. select top 100 * from TransactionTest_01..test01 with(nolock) order by c1 desc;
  72. select top 100 * from TransactionTest_02..test01 with(nolock) order by c1 desc;
  73. 场景1:
  74. --批量删除,执行前重启SQLServer服务
  75. while 1>0
  76. begin
  77.     delete top (5000) from TransactionTest_01..test01 where c1 < 15740000
  78.     if @@rowcount=0
  79.     begin
  80.         break
  81.     end
  82. end
  83. 场景2:
  84. --全量删除,执行前重启SQLServer服务
  85. delete from TransactionTest_02..test01 where c1 < 15740000
复制代码
以下为天生的测试数据(受时间限定,仅天生了16百万的数据):
 
2,测试数据

两个库中,天生测试数据后,测试表的数据库完全划一


 
3,测试数据库的文件巨细

两个库中,天生测试数据之后,测试数据的数据文件和日记文件完全划一。


 
4,删除数据后的事件日记巨细(删除前后均不办事件日记备份)

4.1,批量删除测试库1中的数据,事件日记增长了400MB左右

4.2,整体删数测试库2中的数据,事件日记增长了31G左右

 
5,结论

对于完全一样的表,通过分批多次删除,和一次性删除,删除同样多的数据的环境下:
1,事件日记增长量400MB VS 31000MB,
2,执行耗时,115秒 VS 265秒

这里有一篇很早的文章Break large delete operations into chunks(https://sqlperformance.com/2013/03/io-subsystem/chunk-deletes),也提到单次删除和分批删出的差异性,这篇文测试了很多的场景。
下面这个场景跟本文的场景类似:full recovery模式,单次删除和分批多次删除的对比,

文章的品评区有人问道:why 'chunks delete' generate less logging但答复是说批量删除备份日记,然后日记重用,这个答复并没有表明,在如上图的测试结果中,为什么没有日记备份的环境下,批量删除的日记量远小于单次删除
最终也没有表明出来根本原因:完整恢复模式下,不做日记备份,删除同样多的数据,单次删除和批量多次删除事件日记差异性的原因。
渴望有看到的大佬辅导一二

 

免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?立即注册

x
回复

使用道具 举报

0 个回复

倒序浏览

快速回复

您需要登录后才可以回帖 登录 or 立即注册

本版积分规则

梦见你的名字

论坛元老
这个人很懒什么都没写!
快速回复 返回顶部 返回列表