且构网

分享程序员开发的那些事...
且构网 - 分享程序员编程开发的那些事

任务调度

更新时间:2022-08-19 23:01:13

SQL Server 内置系统调度算法采用:非抢占式争用CPU资源和主动退让策略,主动退让(voluntarily yield)是指在调度器(Scheduler)上运行的Worker都是以非抢占模式来争用CPU资源的。Worker 会一直在一个Scheduler上运行,直到运行结束,或者主动将Scheduler 让出给其他Worker为止。SQL Server定义了很多Yield的规则,约束一个Task占用Scheduler运行的时间,保证Task在合适的时间点主动Yield,不至于占用Scheduler 太多时间,使其他Task等待太久。当Task 主动Yield时,Request处于SOS_SCHEDULER_YIELD等待类型。Worker 也会因为阻塞而主动退让,如果一个Worker在运行过程中被锁或是其他资源阻塞,那么该Worker就会让出Scheduler,来让其它Worker运行,当前Worker处于阻塞状态。

一,消耗CPU资源的操作

在SQL Server中,有三类操作非常消耗CPU资源:

1,编译执行计划,生成执行计划是非常消耗CPU资源的操作,当一个语句生成执行计划之后,SQL Server将其存储在Plan Cache中,以便重用执行计划。

2,执行排序(Sort),聚合计算(Aggregation),哈希连接操作都需要消耗CPU来完成计算,同时Disk IO也需要消耗一定的CPU资源;

3,以并发方式执行查询请求,并发控制受到配置选项 Maximum Degree of Parallelism 和 Cost Threshold of Parallelism的影响。

在发现一个Task比较复杂时,SQL Server会生成多个Child Task,使用多个Thread并发执行该Task,从而提高整体的响应时间,Maximum DOP(Degree of Parallelism)选项控制查询的并发度,决定一个Task在一个时间点最多可以拥有线程的数量。

Cost Threshold of Parallelism 选项决定一个Task是否并发执行。当SQL Server 编译查询语句时,总是先做单线程的执行计划,同时计算执行计划的Cost。如果发现这个执行计划的Cost 值大于Cost Threshold of Parallelism 选项设置的值,那么SQL Server 就会改用并行执行计划。如果提高Cost Threshold of Parallelism 选项的值,SQL Server 会提高做并行执行计划的标准,从而有更少的Task会并发执行,减少CPU的利用,以便留出空闲的CPU执行其他用户的Task。

由于CPU资源的有限,如果为一个Task使用全部的CPU,那么在Task并发执行期间,其他用户的Task得不到及时响应。Task的并发度和用户的并发度时互斥的,为了平衡这种并发度,一般设置Maximum Degree of Parallelism 为CPU总数的1/4,既能够以并发执行计划快速提高单个Task的执行性能,也能兼顾用户的并发度,及时响应其他用户的Request。

二,调度产生的等待类型

1,SOS_SCHEDULER_YIELD

当Task主动Yield时,查询请求处于SOS_SCHEDULER_YIELD等待,等待被重新调用。多数情况下,出现 SOS_SCHEDULER_YIELD 等待是由于查询语句正在进行表或索引扫描,原因可能是缺失相应的索引,统计信息过期,优化器选择差的查询计划,产生参数嗅探,或者查询脚本强制不适用索引等

2,CXPACKET

在查询请求以并行方式运行时,某些 task 在等待其他兄弟Task的处理完成,此时,查询请求处于CXPACKET等待。如果系统中该等待出现次数过多,时间过长,通过增加索引等不能减少该等待,考虑调整增加并发阈值(cost threshold for parallelism)和降低并发度(degree of parallelism)

CXPACKET 等待类型是SQL Server 并发执行一个查询时产生的。在执行查询请求时,SQL Server充分利用系统的所有资源(CPU,Memory,Disk IO),争取在最短时间内返回结果。在拥有多个处理器的系统中,如果将一个查询请求的工作负载(Wordload)分布在多个处理器上,那么每个处理器只处理一部分数据,这将成倍的减少执行查询请求的时间消耗,相应地,成倍的提高查询性能。

在执行Query时,SQL Server 估计其时间消耗,如果大于并发的阈值,那么SQL Server使用多个Thread(每个CPU上在同一时间只能运行一个Thread),以并发方式执行查询请求;如果低于并发阈值,那么SQL Server 使用单个Thread执行查询请iu。这个并发阈值是由选项 cost threshold for parallelism 决定的。

不是所有的query都适合并发执行,并发执行有一定的管理开销(Overhead),如果一个查询耗时十分小,SQL Server 创建并发执行结构体的时间消耗都会比执行整个查询的时间消耗高,那就得不偿失。并发阈值选项(Cost threshold for parallelism)的默认值是5,一般不需要修改默认值。

如果SQL Server 以并发方式执行单个查询请求,那么SQL Server分配的进程数量是由并发度选项(max degree of parallelism )决定的。

在并发执行的Thread中,包括Master Thread,假如MDP=6,那么同时有7个Thread来执行单个查询请求,其中一个Thread是Master Thread,其他被称作Child Thread,Master Thread负责分配任务和将结果结合(combine)在一起,Child Thread负责执行特定的任务。由于Child Thread 被分配的Workload不平均,执行的速度不相同,因此,当一些Child Thread完成任务之后,需要等待未完成的Child Thread。这种在并发执行内部,一些Child Thread需要等待其他Child Thread的Wait type就是:CXPACKET。

使用以下脚本修改默认的并发阈值和并发程度:

任务调度
sp_configure 'show advanced options', 1;
GO
reconfigure;
GO
sp_configure 'cost threshold for parallelism', 6;
GO
reconfigure;
GO

sp_configure 'show advanced options', 1;
GO
RECONFIGURE WITH OVERRIDE;
GO
sp_configure 'max degree of parallelism', 8;
GO
RECONFIGURE WITH OVERRIDE;
GO
任务调度

 

参考文档:

cost threshold for parallelism Option

max degree of parallelism Option

Wait statistics, or please tell me where it hurts

What is the CXPACKET Wait Type, and How Do You Reduce It?

Should you worry about SOS_SCHEDULER_YIELD?

Knee-Jerk Wait Statistics : SOS_SCHEDULER_YIELD

New whitepapers on latches and spinlocks published

作者悦光阴
本文版权归作者和博客园所有,欢迎转载,但未经作者同意,必须保留此段声明,且在文章页面醒目位置显示原文连接,否则保留追究法律责任的权利。
标签: SQL Server







本文转自悦光阴博客园博客,原文链接:http://www.cnblogs.com/ljhdo/p/5149031.html,如需转载请自行联系原作者