Reputation: 339
Is there anyway to get better performance out of this.
SELECT fdyofmth, SUM(total_restored) AS total_restored
FROM sum_restored
WHERE fdyofmth BETWEEN '2010-11-01' AND '2011-11-01'
GROUP BY fdyofmth
ORDER BY fdyofmth DESC
The result takes 3 secs.
+------------+----------------+
| fdyofmth | total_restored |
+------------+----------------+
| 2011-11-01 | 39793 |
| 2011-10-01 | 52367 |
| 2011-09-01 | 52141 |
| 2011-08-01 | 56515 |
| 2011-07-01 | 54668 |
| 2011-06-01 | 54874 |
| 2011-05-01 | 60025 |
| 2011-04-01 | 60005 |
| 2011-03-01 | 63856 |
| 2011-02-01 | 64472 |
| 2011-01-01 | 58943 |
| 2010-12-01 | 57005 |
| 2010-11-01 | 55731 |
+------------+----------------+
EXPLAIN result -
+----+-------------+--------------+------+---------------+------+---------+------+--------+----------------------------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+--------------+------+---------------+------+---------+------+--------+----------------------------------------------+
| 1 | SIMPLE | sum_restored | ALL | NULL | NULL | NULL | NULL | 752660 | Using where; Using temporary; Using filesort |
+----+-------------+--------------+------+---------------+------+---------+------+--------+----------------------------------------------+
1 row in set
I have tried putting a KEY of fdyofmth which actually made it twice as slow.
Any help would be much appreciated.
Thank you.
Upvotes: 2
Views: 182
Reputation: 8295
I think it is slow, because you have so much data, and your sql has to go through all the data(not pick one from the whole data set), so index
can not help here.
The option i propose is use parallelism:
- add the index as suggested by @newtover
- use 12 threads to retrieve the results for each month.
Or even simpler:
just pre-compute the result into another table, when query, query from that table.
Upvotes: 1
Reputation: 32094
According to your EXPLAIN
results, the query doesn't use any indexes. You need to set up an index on fdyofmth
:
ALTER TABLE sum_restored ADD INDEX fdyofmth_index (fdyofmth);
Or another suggestion =):
SELECT
SUM (IF(fdyofmth = '2010-11-01', total_restored, NULL)) as `2010-11-01`,
SUM (IF(fdyofmth = '2010-12-01', total_restored, NULL)) as `2010-12-01`,
SUM (IF(fdyofmth = '2011-01-01', total_restored, NULL)) as `2011-01-01`,
SUM (IF(fdyofmth = '2011-02-01', total_restored, NULL)) as `2011-02-01`,
SUM (IF(fdyofmth = '2011-03-01', total_restored, NULL)) as `2011-03-01`,
SUM (IF(fdyofmth = '2011-04-01', total_restored, NULL)) as `2011-04-01`,
SUM (IF(fdyofmth = '2011-05-01', total_restored, NULL)) as `2011-05-01`,
SUM (IF(fdyofmth = '2011-06-01', total_restored, NULL)) as `2011-06-01`,
SUM (IF(fdyofmth = '2011-07-01', total_restored, NULL)) as `2011-07-01`,
SUM (IF(fdyofmth = '2011-08-01', total_restored, NULL)) as `2011-08-01`,
SUM (IF(fdyofmth = '2011-09-01', total_restored, NULL)) as `2011-09-01`,
SUM (IF(fdyofmth = '2011-10-01', total_restored, NULL)) as `2011-10-01`,
SUM (IF(fdyofmth = '2011-11-01', total_restored, NULL)) as `2011-11-01`
FROM sum_restored;
Upvotes: 0
Reputation: 1545
You should resolve this outside query changes.
Upvotes: 0
Reputation: 100175
Try this: If the dates are not the same, then
SELECT fdyofmth, SUM(total_restored) AS total_restored FROM sum_restored WHERE fdyofmth >= '2010-11-01' AND fdyofmth <= '2011-12-01' GROUP BY fdyofmth ORDER BY fdyofmth DESC
Hope it helps
Upvotes: 0