sql server分区视图执行计划问题

geo*_*170 3 execution-plan sql-server-2008-r2

我已经创建了一个分区视图为3个表tb_sales2010tb_sales2011tb_sales2012使用检查约束(respectivly为每个表)

日期部分(年,[日期])=(2010)
日期部分(年,[日期])=(2011)
日期部分(年,[日期])=(2012)

表 2010 的架构(所有其他表都相同)

CREATE TABLE [dbo].[tb_Sales2010](
    [Date] [smalldatetime] NOT NULL,
    [ID] [int] NOT NULL

 CONSTRAINT [PK_tb_Sales2010] PRIMARY KEY NONCLUSTERED 
(
    [ID] ASC
)WITH (PAD_INDEX  = OFF, STATISTICS_NORECOMPUTE  = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS  = ON, ALLOW_PAGE_LOCKS  = ON) ON [PRIMARY]
) ON [PRIMARY]

GO

ALTER TABLE [dbo].[tb_Sales2010]  WITH CHECK ADD  CONSTRAINT [CK_Date_2010] CHECK  ((datepart(year,[Date])=(2010)))
GO
Run Code Online (Sandbox Code Playgroud)

我的查询是

SELECT TOP 1 *
FROM partitionedTb_sales
WHERE DATEPART(YY, DATE) = 2011
Run Code Online (Sandbox Code Playgroud)

我的问题是,执行计划表明它正在扫描所有 3 个表。而不是查看检查约束并说表 b 具有它需要的信息。这是为什么。我觉得执行计划应该只显示 1 个正在扫描的表。

在此处输入图片说明

统计开启结果

表“工作台”。扫描计数 0,逻辑读 0,物理读 0,预读 0,lob 逻辑读 0,lob 物理读 0,lob 预读 0。

表 'tb_Sales2012'。扫描计数 1,逻辑读取 3,物理读取 0,预读读取 0,lob 逻辑读取 0,lob 物理读取 0,lob 预读读取 0。

表 'tb_Sales2011'。扫描计数 1,逻辑读取 3,物理读取 0,预读读取 0,lob 逻辑读取 0,lob 物理读取 0,lob 预读读取 0。

表 'tb_Sales2010'。扫描计数 1,逻辑读取 3,物理读取 0,预读读取 0,lob 逻辑读取 0,lob 物理读取 0,lob 预读读取 0。

视图定义 CREATE VIEW PartitionedTb_Sales AS SELECT * FROM tb_sales2010

联合所有

SELECT * FROM tb_sales2011

联合所有

SELECT * FROM tb_sales2012

Tim*_*imG 7

在可以完成/计算任何过滤之前,仍然必须对每一行执行 DATEPART() 函数。

如果你像这样改变它,你的视图会更有效率:

CREATE VIEW PartitionedTb_Sales 
AS 
SELECT *, 2010 AS SalesYear FROM tb_sales2010
UNION ALL
SELECT *, 2011 AS SalesYear FROM tb_sales2011
UNION ALL
SELECT *, 2012 AS SalesYear FROM tb_sales2012
Run Code Online (Sandbox Code Playgroud)

然后,不是使用 DATEPART() 来计算每一行的年份,而是已经定义好了。

SELECT TOP 1 *
FROM partitionedTb_sales
WHERE SalesYear = 2011
Run Code Online (Sandbox Code Playgroud)