我在Server 2008中有如下查询:
SELECT
a.type,
a.name,
a.startDate,
a.endDate,
b.key AS key,
b.is_locked AS is_locked,
NULL AS idx,
NULL AS page_count
FROM
jobs a LEFT JOIN gates b ON a.pk_job = b.fk_job
WHERE
a.status IN (0,1,7)
AND a.startDate > DATEADD(dd, DATEDIFF(dd, 0, getdate()), 0)
AND a.type in (15,17,19)
UNION ALL
SELECT
a.type,
a.name,
a.startDate,
a.endDate,
NULL AS key,
NULL AS is_locked,
c.idx AS idx,
c.page_count AS page_count
FROM
jobs a LEFT JOIN pages c ON a.pk_job = c.fk_job
WHERE
a.status = 5
AND a.startDate = DATEADD(dd, DATEDIFF(dd, 0, getdate()), 0)
AND a.type in (15,17,19)我将查询简化如下:
SELECT * FROM
(
SELECT
a.type,
a.name,
a.startDate,
a.endDate,
b.key AS key,
b.is_locked AS is_locked,
NULL AS idx,
NULL AS page_count
FROM
jobs a LEFT JOIN gates b ON a.pk_job = b.fk_job
WHERE
a.status IN (0,1,7)
AND a.startDate > DATEADD(dd, DATEDIFF(dd, 0, getdate()), 0)
UNION ALL
SELECT
a.status,
a.name,
a.startDate,
a.endDate,
NULL AS key,
NULL AS is_locked,
c.idx AS idx,
c.page_count AS page_count
FROM
jobs a LEFT JOIN pages c ON a.pk_job = c.fk_job
WHERE
a.status = 5
AND a.startDate = DATEADD(dd, DATEDIFF(dd, 0, getdate()), 0)
) t
WHERE t.type IN (15,17,19)我想知道简化的查询是否比原来的查询性能更好?
注意:如果有语法错误,请在注释部分告诉我,因为我用我的手输入了这个查询。
还有一点OOT问题:
简化上述表示或逻辑的过程的英文术语是什么?通过将两个相同的where条件(t.type IN (15,17,19))简化成一个?
另一个例子如下:
R = (x+2)/2 + (x+3)/2您可以通过删除重复的"/2“来简化它,如下所示:
R = ( (x+2) + (x+3) ) / 2您可以在评论部分回答OOT问题。
提前谢谢。
发布于 2013-03-20 16:47:51
您不需要子查询,只需一次I/O,您将获得更好的性能:
select * from jobs
where (
(status IN (0,1,7) and startDate > getdate())
or (statu=5 and startDate=getdate())
)
and type in (15,17,19)发布于 2013-03-21 16:37:46
在性能调优查询中没有硬性规则。如果将简单查询A1和A2与A2作为A1的“缩减”版本进行比较,您可能会发现A2比A1更快。但是,这并不意味着两个复杂的查询-- B1和B2 --使用相同的简化过程,B2是B1的简化版本,这两个查询将显示相同的性能关系。
上面的查询使用表别名a和c,这意味着表b也涉及到。一旦添加了额外的连接,优化器将采用完全不同的路径,并且不能再将优化结果从一个比较到另一个。
在完美世界中,查询的任何“缩减”都不会改变优化的结果,因为目标是找到回答问题的完美查询计划。但是,由于搜索计划需要时间,而且时间很容易超过执行查询所需的时间,因此SQL Server为“足够好”的计划做好了准备。为了达到这个目的,它使用了一组启发式方法。
通常,Server优化器非常接近最佳计划。然而,对于非常复杂的查询,它有时会被“卡住”在死胡同搜索路径中。通过重写查询,我们可以更改优化器的起点,这样它就不会在同一个兔子洞中结束。但是,一般来说,这不是必需的(至少在最后三个Server版本中是这样的)。
现在,如果您的查询是性能问题,那么首先要考虑的是适当的索引。如果您给我们完整的查询,我们可能会在这方面有所帮助。
如果索引没有足够的帮助,我们可以开始研究重写的可能性,但是同样,我们需要对此进行完整的查询,并且可能还需要大量的示例数据。
如果您已经查看了索引,但仍然需要帮助,则发布查询和实际(执行后) XML查询计划。
发布于 2013-03-20 16:46:07
在我看来,您并没有真正简化查询。如果联合子查询提供了大量的结果,那么性能可能会更差。最好是这样。
SELECT
*
FROM jobs
where 1=1
and type in (15,17,19)
and (1=2
or (1=1
and status IN (0,1,7)
AND startDate > getdate()
)
or (1=1
and status = 5
AND startDate = getdate()
)
)此外,startDate = getdate()部分对我来说似乎很棘手--它不太可能“命中”startDate,因为getdate()给您当前的时间不超过3/数千秒。
https://dba.stackexchange.com/questions/37205
复制相似问题