Rao*_*bin 16 performance sql-server-2008 sql-server index-tuning
这个问题是关于 SQL Server 索引性能,a varchar(2000)as an INCLUDEin a coverage index。
我正在尝试提高缓慢且不稳定的数据库应用程序的性能。在某些情况下,数据是通过大VARCHAR字符串来访问的,与查询包括像multple字符串操作SUBSTRING(),SPACE()和DATALENGTH()。这是访问的简化示例;
update fattable set col3 =
SUBSTRING(col3,1,10) + '*' +
SUBSTRING(col3,12,DATALENGTH(col3)-12)
from fattable where substring(col3,10,1) = 'A' and col2 = 2
Run Code Online (Sandbox Code Playgroud)
架构如下所示:
CREATE TABLE [dbo].[FatTable](
[id] [bigint] IDENTITY(1,1) NOT NULL,
[col1] [nchar](12) NOT NULL,
[col2] [int] NOT NULL,
[col3] [varchar](2000) NOT NULL, ...
Run Code Online (Sandbox Code Playgroud)
定义了以下索引,在大文本列上有一个覆盖字段。
CREATE NONCLUSTERED INDEX [IndexCol2Col3] ON [dbo].[FatTable] ( [col2] ASC )
INCLUDE( [col3] )
Run Code Online (Sandbox Code Playgroud)
从我读过的内容来看,将大数据字段放在索引中是很糟糕的。我一直在阅读几篇文章,包括http://msdn.microsoft.com/en-us/library/ms190806.aspx,其中讨论了分页和磁盘大小对索引性能的影响。话虽如此,查询计划肯定会使用覆盖索引。我没有足够的信息来确定这在系统负载方面实际上给我带来了多少成本。我确实知道总体而言,系统性能不佳,我担心这是问题之一。问题:
将此varchar(2000)列放在索引中INCLUDE是个好主意吗?
由于INCLUDE字段存储在叶节点中,它们对索引性能有很大影响吗?
更新:感谢您的出色回复!在某些方面,这是一个不公平的问题 - 正如你们所说,没有实际的统计数据和分析,就没有绝对正确的答案。像许多性能问题一样,我想答案是“视情况而定”。
Gra*_*hey 14
Ever 是一个大词,但总的来说,不,我不会将 varchar(2000) 字段放入 INCLUDE 中。
是的,在页面级别存储数据的方式会严重影响索引的性能,具体取决于索引的使用方式。
问题是,您可以塞进一个页面的数据行越多,需要访问的页面就越少,您的系统在大多数情况下就越快。添加一个非常大的列意味着页面上存储的信息更少,因此,在范围搜索或扫描的情况下,必须读取更多页面来检索数据,这会严重减慢速度。
要确定这是否是您的查询或系统上的问题,您必须监视读取,尤其是查询使用的页数。
您能否查看当前的聚集索引键,并可能col2改为创建聚集索引键?通过这种方式,您可以获得覆盖“包含”行为(因为聚集索引总是“包含”所有内容)而无需复制数据。这当然是受到很多if和but,然而或许是值得考虑的。当然,如果当前聚集索引强制执行约束(主键、唯一键),则必须将所述约束移动到非聚集索引中。