0

我有一个在超过 60 万条记录上运行的 mysql SUM 查询。我目前正在做的是这样的

 SELECT SUM (payment)
    FROM payment_table
    WHERE
       payment_date BETWEEN ... AND ...
       AND
       payment_status = 'paid'

我将查询更改为这种格式以减少记录集,但它仍然需要几乎相同的时间。

SELECT SUM(Payments)
FROM (
    SELECT payment AS Payments FROM payment_table WHERE
     payment_date BETWEEN DATE_FORMAT(NOW(), '2012-2-01') AND DATE_FORMAT(LAST_DAY(DATE_FORMAT(NOW(), '2012-2-01')), '%Y-%m-%d')
    AND
    payment_status = 'paid'
) AS tmp_table

他们有什么方法可以优化这个总和查询。编辑:

这是查询运行时的结果EXPLAIN

插入` (id ,select_type ,table ,type ,possible_keys , key ,key_len ,ref ,rows ,Extra`) values('1','SIMPLE','lps','index_merge','assigned_user_id,scheduled_pa​​yment_date,payment_status,deleted','deleted,assigned_user_id,payment_status', '2,109,303',NULL,'23347','使用 intersect(deleted,assigned_user_id,payment_status); 使用 where');

4

1 回答 1

1

您应该将谓词的数据类型与列相匹配。因为payment_typeis DATE,所以也使 BETWEEN 值DATE

 WHERE payment_date BETWEEN
     CURDATE() AND LAST_DAY(CURDATE())

匹配类型可确保使用索引。


相反,您的查询正在使用DATE_FORMAT(),它产生一个文本数据类型,所以为了执行比较,mysql 正在将payment_dare列转换为文本,所以它不能使用索引(索引包含DATE值,而不是文本值),所以每一行都被转换和比较。


如果您在进行上述更改后仍然遇到性能问题,请执行以下操作:

ANALYZE TABLE payment_table;

这将检查索引列中值的分布,这有助于 mysql 做出正确的索引选择。

于 2013-03-11T11:40:26.017 回答