本文属于SQL Server T-SQL执行内幕系列
每当操作读取页的数据,意味着这些数据需要固定到缓存(buffer pool)中。这个时候可能会导致操作被阻塞,因为当所需要的数据不在内存时,需要把数据从磁盘载入内存,这个时候操作需要等待页从磁盘搜索并载入内存。如果由于系统负担很重或者载入的量很大,磁盘I/O响应不及时,那么此时操作就会被阻塞(stall),性能将会暴跌。
从现实生活来说,我们对于这种情况,可以通过一次加载相关的大量数据减少多次加载,同时让内存足够大也能避免多次加载,最后就是增加磁盘I/O子系统的性能。
为了解决这种问题,SQL Server引入了read ahead技术,本质上就是先加载前面没有被引用,但是又很快会被引用的页。它在操作实际访问这些页并读取行之前,根据扫描操作的要求使用异步方式提前发出请求。
有时候如果使用SET STATISTICS IO 来查看语句IO行为时,可能会看到类似:
Table'MythOne'. Scan count 1, logical reads 1495, physical reads 0, read-ahead reads 0, lob logical reads 0, lob physical reads 0, lob read-ahead reads 0.
对于Read Ahead的深入介绍可以看下面三篇,同样,read ahead很难通过用户干预来影响,我们能做的就是完善硬件性能,改进写法、索引设计。