SQL Server 存储中间结果集
在SQL Server中执行查询时,有一些操作会产生中间结果集,例如:排序操作,Hash Join和Hash Aggregate操作产生的Hash Table,游标等,SQL Server查询优化器使用 Worktable 和 Workfile 存储中间结果集,对中间结果集执行后续操作,以响应用户的请求。
一,Spool 操作符
Spool的中文解释是假脱机,是指两个设备处于联机状态,只不过都在后台运行。
假脱机的原理,通俗的说,是在两个设备之间进行数据交换,一个设备传输数据的速度快,一个设备传输数据的速度慢。为了充分利用高速设备,在需要交换数据时,低速设备将数据输入到缓冲区,同时,高速设备无需等待低速设备,而是径直去处理其他Task,等低速设备将全部数据输入到缓存之后,高速设备再去缓冲区读取数据,然后快速处理,这样高速设备就不会闲置,提高设备的利用率。Spool 为了协调两个设备,需要用到一个缓冲区,低速设备向缓冲区中写数据,高速设备从缓冲区中读取数据。所以,假脱机技术的原理,是低速设备在后台利用缓冲区转存数据,高速设备从缓冲区获取数据,执行数据处理。
在 SQL Server的执行计划中,Spool 是逻辑运算符,分为Eager Spool 和 Lazy Spool:
- Eager Spool 逻辑运算符:一次性将所有数据输入到临时的Spool中
- Lazy Spool 逻辑运算符:逐批将数据输入到临时的Spool中
如果执行计划出现这两个操作符,表明 SQL Server 需要将中间结果集保存到临时存储区,在SQL Server中,临时存储区是指Worktable 或 Workfile, 用于存储临时结果集:
- WorkFile: 用于存储Hash Join 和 Hash 聚合的临时结果集,小的临时结果集存储在Memory中;
- WorkTable: 用于存储 Query Spool(table spool, index spool, and so on),Lob 变量,XML变量和游标的临时结果集;
- Spill to tempdb:WorkFile和WorkTable都创建在内存中,如果临时结果集太大,分配的Memory容纳不了,那么,临时结果集会被保存到tempdb file中,即:spill to disk(tempdb files);
- 查询性能降低:一般来说,SQL Server在执行计划中使用WorkFile 或 WorkTable,表明查询语句的性能较低
引用MSDN:
"Work files could be used to store temporary results for hash joins and hash aggregates. The returned value should be less than 20. Tempdb work files are used in processing hash operations when the amount of data being processed is too large to fit into the available memory." Possible problems: High values can indicate thrash in the tempdb file as well as poorly coded queries.
"Work tables could be used to store temporary results for query spool, lob variables, XML variables, and cursors. The returned value should be less than 20. Worktables are used for queries that use various spools (table spool, index spool, and so on)." Possible problems: High values could cause general slowdown.
二,查看Workfile 和 Worktable
查询优化器创建Workfile 和 Worktable 的目的是为了存储临时结果集,在执行查询时,设置 “Set Statistics IO On” ,能够看到查询语句创建的 Workfile 和 Worktable,以及临时存储区的IO信息,如图:
一般情况下,如果临时存储对象(Workfile 和 Worktable)被创建,说明查询的中间结果集太大,服务器的内存资源将被耗尽,导致SQL Server 必须使用Disk存储中间结果集,才能使查询操作继续执行,但是,可用的内存耗尽和额外的IO开销,都会降低SQL Server的的查询性能。
SQL Server在内存中创建Workfile 和 Worktable,在中间结果集较小时,中间结果集保存在内存中;如果结果集过大,保存在内存将增加内存压力,SQL Server将中间结果集转存到tempdb的数据文件中,即,从内存写入到Disk。在需要中间结果集时,从Disk File读取到内存中,产生额外的Disk IO,降低SQL Server的查询性能。
1,使用Worktable
关系引擎在执行 order by、group by或者union操作时,需要创建WorkTable,用于保存中间结果集。例如,在执行Order by 操作时,如果没有在排序字段上创建index,那么SQL Server查询优化器会在tempdb中创建一个WorkTable来缓存中间查询结果集,并对中间结果集进行排序。在系统需要时,自动创建创建在tempdb中创建WorkTable;当系统不再需要该WorkTable时,会自动从tempdb中删除。
优化方法:为了减少WorkTable的使用,应该优化SQL语句,减少不必要的group by,order by或Union操作,在select 子句中剔去不必要的column,使返回的结果集尽可能的小。
引用MSDN:
The relational engine may need to build a worktable to perform a logical operation specified in an SQL statement. Worktables are internal tables that are used to hold intermediate results. Worktables are generated for certain GROUP BY, ORDER BY, or UNION queries. For example, if an ORDER BY clause references columns that are not covered by any indexes, the relational engine may need to generate a worktable to sort the result set into the order requested. Worktables are also sometimes used as spools that temporarily hold the result of executing a part of a query plan. Worktables are built in tempdb and are dropped automatically when they are no longer needed.
2,使用WorkFile
在SQL Server执行Hash Join 或 Hash聚合操作,使用WorkFiles来存储临时结果集。
Hash Join 能够有效处理大量,未排序,未索引的输入;Hash Join在处理复杂查询返回的中间结果集时非常有用,是因为:
Intermediate results are not indexed (unless explicitly saved to disk and then indexed) and often are not suitably sorted for the next operation in the query plan.
Query optimizers estimate only intermediate result sizes. Because estimates can be very inaccurate for complex queries, algorithms to process intermediate results not only must be efficient, but also must degrade gracefully if an intermediate result turns out to be much larger than anticipated.
优化方法:为了减少WorkFile的使用,在和大表进行Join查询时,尽可能地使用Index Column,避免对无序数据进行Hash Join或Hash 聚合操作。
参考文档:
Operator of the Week – Spools, Eager Spool
SET STATISTICS IO- worktable/workfile
Beware misleading data from SET STATISTICS IO
Simple Query tuning with STATISTICS IO and Execution plans
Advanced Query Tuning Concepts
SQL Server, Access Methods Object
workfiles created/sec spiking out of control
SQL Server 存储中间结果集的更多相关文章
- SQL Server故障转移集群
在XenServer集群上给客户搭建一个应用服务,要求有负载均衡,Web服务器用Windows Server 2008 R2 + IIS,数据库Sql Server 2008 R2,并且使用SAN存储 ...
- SQL SERVER存储引擎——04.数据
4. SQL SERVER存储引擎之数据篇 (4.1)文件 (0)主数据文件.mdf初始文件大小至少为3MB,次要数据文件.ndf初始大小,同日志文件一样至少为512KB: (1)SQL SERVER ...
- SQL Server存储ntext截断问题
SQL Server存储ntext截断问题 最近遇到一个问题:将大文本存储到数据库的时候,查询出来的文本却被截断了. 最后百度发现,作者提出 sql server management studi ...
- SQL Server 2012 AlwaysOn集群配置指南
1. AlwaysOn介绍 AlwaysOn是SQL Server 2012提供的全新综合.灵活.高效经济的高可用性和灾难恢复解决方案.它整合了镜像和群集的功能,基于OS 故障转移群集(Windows ...
- SQL Server 存储(1/8):理解数据页结构
我们都很清楚SQL Server用8KB 的页来存储数据,并且在SQL Server里磁盘 I/O 操作在页级执行.也就是说,SQL Server 读取或写入所有数据页.页有不同的类型,像数据页,GA ...
- SQL Server 存储(3/8):理解GAM和SGAM页
我们知道SQL Server在8K 的页里存储数据.分区就是物理上连续的8个页.当我们创建一个数据库,数据文件会被逻辑分为页和区,当用户对象创建时,页会分配给它用来存储数据.GAM(Global Al ...
- SQL Server 存储(5/8):理解IAM 页
在以前的文章里,我们讨论了数据页,GAM和SGAM,还有PFS页.今天我们一起来讨论下索引分配映射(Index Allocation Map:IAM)页. 在SQL Server 2005和以后的版本 ...
- SQL Server 存储引擎-剖析Forwarded Records
我们都知道数据在存储引擎中是以页的形式组织的,但数据页在不同的组织形式中其中对应的数据行存储是不尽相同的,这里通过实例为大家介绍下堆表的中特有的一种情形Forwared Records及处理方式. 概 ...
- SQL Server 存储(2/8):理解数据记录结构
在SQL Server :理解数据页结构我们提到每条记录都有7 bytes的系统行开销,那这个7 bytes行开销到底是一个什么样的结构,我们一起来看下. 数据记录存储我们具体的数据,换句话说,它存在 ...
随机推荐
- Unity 序列化
Script Serialization http://docs.unity3d.com/Manual/script-Serialization.html 自定义序列化及例子: http://docs ...
- Android数据存储之Android 6.0运行时权限下文件存储的思考
前言: 在我们做App开发的过程中基本上都会用到文件存储,所以文件存储对于我们来说是相当熟悉了,不过自从Android 6.0发布之后,基于运行时权限机制访问外置sdcard是需要动态申请权限,所以以 ...
- CSS 3学习——边框
在CSS 3中可以设置边框圆角.边框阴影和边框图像,分别通过border-radius.border-image和box-shadow属性设置. 边框圆角 border-radius属性是以下4个属性 ...
- .Net语言 APP开发平台——Smobiler学习日志:如何快速在手机上实现ContextMenu
最前面的话:Smobiler是一个在VS环境中使用.Net语言来开发APP的开发平台,也许比Xamarin更方便 样式一 一.目标样式 我们要实现上图中的效果,需要如下的操作: 1.从工具栏上的&qu ...
- 【夯实PHP基础】UML序列图总结
原文地址 序列图主要用于展示对象之间交互的顺序. 序列图将交互关系表示为一个二维图.纵向是时间轴,时间沿竖线向下延伸.横向轴代表了在协作中各独立对象的类元角色.类元角色用生命线表示.当对象存在时,角色 ...
- Android之使用文件进行IPC
一.文件进行IPC介绍 共享文件也是一种不错的进程间通信方式,两个进程通过读/写同一个文件来交换数据.在Windows上,一个文件如果被加了排斥锁将会导致其他线程无法对其进行访问,包括读写,而由于An ...
- 小程序用户反馈 - HotApp小程序统计仿微信聊天用户反馈组件,开源
用户反馈是小程序开发必要的一个功能,但是和自己核心业务没关系,主要是产品运营方便收集用户的对产品的反馈.HotApp推出了用户反馈的组件,方便大家直接集成使用 源码下载地址: https://gith ...
- [转载]敏捷开发之Scrum扫盲篇
现在敏捷开发是越来越火了,人人都在谈敏捷,人人都在学习Scrum和XP... 为了不落后他人,于是我也开始学习Scrum,今天主要是对我最近阅读的相关资料,根据自己的理解,用自己的话来讲述S ...
- BZOJ 1010: [HNOI2008]玩具装箱toy [DP 斜率优化]
1010: [HNOI2008]玩具装箱toy Time Limit: 1 Sec Memory Limit: 162 MBSubmit: 9812 Solved: 3978[Submit][St ...
- .NET全栈开发工程师学习路径
PS:最近一直反复地看博客园以前发布的一条.NET全栈开发工程师的招聘启事,觉得这是我看过最有创意也最朴实的一个招聘启事,更为重要的是它更像是一个技术提纲,能够指引我们的学习和提升,现在转载过来与各位 ...