为时态查询中使用的表建立索引

时间:2013-01-31 18:15:14

标签: sql sql-server tsql indexing

我有一个结构表:

 CREATE TABLE [dbo].[rx](
            [pat_id] [int] NOT NULL,
            [fill_Date] [date] NOT NULL,
            [script_End_Date]  AS (dateadd(day,[dayssup],[filldate])),
            [drug_Name] [varchar](50) NULL,
            [days_Sup] [int] NOT NULL,
            [quantity] [float] NOT NULL,
            [drug_Class] [char](3) NOT  NULL,
            [ofInterest] bit
            CHECK(fill_Date <=script_End_Date
PRIMARY KEY CLUSTERED 
(
            [clmid] ASC
)


CREATE TABLE [dbo].[Calendar](
             [cal_date] [date] PRIMARY KEY,
[Year] AS YEAR(cal_date) PERSISTED,
[Month] AS MONTH(cal_date) PERSISTED,
[Day] AS DAY(cal_date) PERSISTED,
             [julian_seq] AS 1+DATEDIFF(DD, CONVERT(DATE, CONVERT(varchar,YEAR(cal_date))+'0101'),cal_date),
     id int identity);

我在这个查询中使用了这些表:

;WITH x 
     AS (SELECT rx.pat_id, 
                c.cal_date, 
                Count(DISTINCT rx.drug_name) AS distinctDrugs 
         FROM   rx, 
                calendar AS c 
         WHERE  c.cal_date BETWEEN rx.fill_date AND rx.script_end_date 
                AND rx.ofinterest = 1 
         GROUP  BY rx.pat_id, 
                   c.cal_date 
         --the query example I used having count(1) =2, but to illustrate the non-contiguous intervals, in practice I need the below having statement
         HAVING Count(*) > 1), 
     y 
     AS (SELECT x.pat_id, 
                x.cal_date 
                --c2.id is the row number in the calendar table. 
                , 
                c2.id - Row_number() 
                          OVER( 
                            partition BY x.pat_id 
                            ORDER BY x.cal_date) AS grp_nbr, 
                distinctdrugs 
         FROM   x, 
                calendar AS c2 
         WHERE  c2.cal_date = x.cal_date) 
SELECT *, 
       Rank() 
         OVER( 
           partition BY pat_id, grp_nbr 
           ORDER BY distinctdrugs) AS [ranking] 
FROM   y 

日历表运行三年,rx表中有大约800k行。在前面的查询运行了几分钟后,我决定为它添加一个索引以加快速度。我添加的索引是

create index ix_rx
on rx (clmid)
include (pat_id,fill_date,script_end_date,ofinterest)

此索引对查询的运行时间没有任何影响。任何人都可以帮助解释为什么没有使用上述索引?这是一个回顾性数据库,不再添加任何数据。如果需要,我可以添加执行计划。

2 个答案:

答案 0 :(得分:2)

查询中根本没有使用clmid字段。因此,如果优化器会考虑它,我会感到惊讶,只是对于包含列。

如果要使用索引加速查询,请从使用该表的查询开始。使用的字段为pat_iddrug_namerx_ofinterestfill_datescript_end_date。最后两个因为中间因素而具有挑战性。您可以尝试使用此索引:rx(pat_id, drug_name, ofinterest, fill_date, script_end_date)

索引中包含所有引用的字段,可以在不加载数据页的情况下访问数据。

答案 1 :(得分:0)

因为它不是合适的索引。在[pat_id]上创建两个索引,在drug_name上创建另一个索引。 -