分组通过使查询在天文学上更长

时间:2012-12-12 16:54:46

标签: sql optimization db2 squirrel-sql

*作为第一个注释,我只能访问我的服务器。只是,仅供参考,因为它似乎出现了很多......

服务器:DB2(6.1)for i(IBM)

我有一个查询我正在一个有19mil行的表上运行(我不设计它们,我只是查询它们)。我一直将我的返回数据限制为10行(*),直到我将这个查询整理出来,以便返回时间更合理。

基本设计是我需要逐周获取有关我们销售的产品类别的数据,使用列:WEEK_ID和CATEGORY。这是示例代码(带有一些重要的位#### out。)

SELECT WEEK_ID, CATEGORY
FROM DWQ####.SLSCATW
INNER JOIN DW####.CATEGORY
ON DWQ####.SLSCATW.CATEGORY_NUMBER = DW####.CATEGORY.CATEGORY_NUMBER
WHERE WEEK_ID  
BETWEEN 200952 AND 201230 --Format is year/week
GROUP BY WEEK_ID, CATEGORY

如果我注释掉最后一行,我可以在254毫秒内返回100行。如果我把这条线放回到我的回程中需要的时间比我耐心等待的时间要长:-)。 (我等待的最长时间是10分钟。)

这个问题有两个部分。第一个问题很简陋:这是正常的吗?有50个类别(大致)和140周(左右)我正在努力缩减。我意识到有很多信息要缩小19mil的行,但我希望将我的查询限制为10行返回会最小化时间量?

而且,如果我不仅仅是一个完整的n00b,而且实际上这不应该花费几分钟,我的SQL究竟出了什么问题?

我用Google搜索WHERE语句优化,但似乎找不到任何东西。所有链接和解释都非常受欢迎。

为这样一个新手发帖道歉...我们都必须从某个地方开始,对吧?

(*)使用我的IDE SQLExplorer,一个Squirrel SQL的Eclipse实现。

2 个答案:

答案 0 :(得分:2)

当查询中没有聚合函数时,我不确定服务器如何处理group by。根据您在评论中的答案,我只想尝试添加:

SELECT
    ...,
    SUM(SalesCost) as SalesCost,
    SUM(SalesDollars) as SalesDollars
FROM
    ...

保留查询的其余部分。

如果这不能解决问题,则可能缺少索引。我会尝试找出是否有一个索引,其中WEEK_ID是唯一的列,它是第一个列。您还可以检查是否在已编制索引的同一个表上有另一个临时列(即TransactionDate或类似的东西)。如果是这样,您可以在where子句中使用它。

如果没有正确的索引,数据库服务器将被强制执行完整的表扫描,这可以解释您的性能问题。 3900万行确实需要花费一些时间来从磁盘读取。

同时检查WEEK_ID的数据类型是否为int或类似,以避免在查询中进行不必要的转换。

要避免对Category表进行表扫描,您需要确保也为Category_Number建立索引。 (它可能已经存在,因为我认为它是该表的关键。)

答案 1 :(得分:0)

WEEK_ID,CATEGORY(以及可能的CATEGORY_NUMBER)上的索引是使其非常快的唯一方法,因此您需要说服DBO引入这些索引。