2016-09-20 4 views
0

У меня SQL-запрос, который занимает слишком много времени, на мой взгляд, около 30 секунд, как сейчас выглядит. У меня есть две таблицы: Record и Mainrecord. Я хотел бы получить информацию обо всех основных рекордах, которые имеют 0 в размере столбца, а также в этом случае получить последнюю запись с тем же идентификатором, у которого есть что-то другое, кроме 0 в своей сумме. У меня около 30 000 основных рекордов и около 3 000 000 записей. Я предполагаю, что это может быть оптимизировано каким-то образом, но я не могу понять это.Внутреннее соединение между таблицами, занимающее много времени

SELECT * 
FROM (
    mainrecord 
    INNER JOIN (
     SELECT tt.* 
     FROM record tt 
     INNER JOIN (
      SELECT Max(record.timestamp) AS maxtimestamp, id 
      FROM record 
      WHERE record.amount <> 0 
      GROUP BY record.id 
     ) AS rec 
     ON tt.id = rec.id AND tt.timestamp = rec.maxtimestamp 
    ) AS t 
    ON mainrecord.id = t.id 
) 
WHERE amount = 0 

EXPLAIN:

+----+-------------+------------+-------------+---------------+-----------+---------+---------------------+---------+----------+---------------------------------------+ 
| id | select_type | table | type  | possible_keys | key | key_len |   ref   | rows | filtered |     Extra     | 
+----+-------------+------------+-------------+---------------+-----------+---------+---------------------+---------+----------+---------------------------------------+ 
| 1 | PRIMARY  | Mainrecord | index_merge | Id,Amount  | Amount |  768 | \N     | 2850 | 100,00 | Using sort_union(Amount); Using where | 
| 1 | PRIMARY  | <derived3> | ref   | key0   | key0  |  768 | db.Mainrecord.Id |  53 | 100,00 | Using where       | 
| 1 | PRIMARY  | tt   | ref   | Id,timestamp | timestamp |  9 | record.maxtimestamp |  1 | 100,00 | Using where       | 
| 3 | DERIVED  | Record  | index  | Amount  | Id  |  768 | \N     | 3185669 | 50,03 | Using where       | 
+----+-------------+------------+-------------+---------------+-----------+---------+---------------------+---------+----------+---------------------------------------+ 
+1

Есть ли у вас какие-либо показатели? Также, пожалуйста, добавьте результаты «Объяснить» на вопрос. – Shaharyar

+0

Кто такой главный стол ?? –

+0

@Shaharyar, оба id и amout являются ключами в обеих таблицах. – Nick3

ответ

0

Что об этом? Чтобы извлечь группировку из подзапросов

ОБНОВЛЕНО:

SELECT * 
FROM mainrecord mr 
    INNER JOIN (SELECT Max(record.timestamp) AS maxtimestamp, id 
     FROM record 
     WHERE record.amount <> 0 
     GROUP BY record.id) AS max_r ON max_r.id=mr.id 
    INNER JOIN record r ON mr.id = r.id 
WHERE mr.amount = 0 
    AND r.timestamp = max_r.maxtimestamp 
+0

Спасибо, но я не понимаю, как это работает. Я думаю, что 'FROM Record' должен быть' FROM record tt'. Я также удалил ')' после 'rec.maxtimestamp', поскольку количество скобок не совпало. Ошибка, которую я получаю сейчас, это Синтаксическая ошибка: 'AS max_r ON max_r.id = mr.id INNER JOIN record r ON mr.id = r.id' – Nick3

+0

Я не могу правильно проверить sytax. Создайте SQlFiddle, чтобы я мог протестировать запрос – StanislavL

+0

http://sqlfiddle.com/#!9/430e02/1/0 test с этим, я добавил очень легкую структуру, содержащую все элементы, которые мы используем. – Nick3

Смежные вопросы