2015-12-19 2 views
0

Я пытаюсь выяснить, как я могу улучшить производительность этого запроса, и я считаю, что это могут быть мои индексы; некоторые из моих мыслей о том, что дата может быть причиной плохой производительности или что у меня индексы в порядке неправильны. Также есть ли какие-либо другие предложения о том, как улучшить скорость, не связанную с индексом? Спасибо, я с нетерпением жду любого ввода!Настройка производительности Mysql

Вот что я пытался до сих пор

ALTER TABLE data ADD INDEX(data_timestamp, first,last); 
ALTER table data add index(first); 
ALTER table data add index(first); 
ALTER TABLE data add index (data_timestamp); 

следующий запрос (второй) ниже запускает подзапрос для каждой строки базы данных для того, чтобы получить предыдущий средний в момент каждой точки

select count(*) from data where data_timestamp like '2015-01-01%'; -> 362855 

select (select sum(first*last)/sum(last) 
FROM data t2 
WHERE data_timestamp like '2015-12-18%' 
AND t2.data_timestamp <= t1.data_timestamp 
), t1.* 
FROM data t1 
WHERE data_timestamp like '2015-12-18%'; 
+0

Опубликовать объяснение, а также сколько строк в данных? Всего. – Mihai

+0

Вы можете попробовать http://stackoverflow.com/questions/664700/calculate-a-running-total-in-mysql –

+0

Общее количество строк: 362855 – kevinn2065

ответ

0

Вы можете запросить «объяснение» в базе данных, чтобы выяснить, что происходит. Просто напишите «объясните» перед любым запросом.

Нет необходимости добавлять индексы для первого и последнего. Вы только ищете в полях data_timestamp, так что это единственный индекс, который вам нужен.

С другой стороны, у вас могут возникнуть проблемы с использованием столбцов «как%» в столбцах даты. Проверьте, есть ли другие альтернативы, чтобы сделать то же самое. Если data_timestamp является текстовым столбцом, вы должны добавить в поле полный текстовый индекс. Если data_timestamp является столбцом даты, используйте «между» вместо «like». «Объяснить» указывает, какой индекс используется в запросе.

2

Для обеспечения оптимальной производительности вам нужна операция сканирования диапазона индекса для столбца data_timestamp. Предикат в запросе формы:

WHERE data_timestamp LIKE '2015-12-18%' 

навязывает MySQL оценить все значение data_timestamp в таблице, эффективно преобразование/значения временной метки DateTime в строку, а затем выполняет сравнение строк на преобразованном значении ,

Если мы используем предикат со сравнением с значениями даты и времени, то MySQL может более эффективно использовать индекс, который имеет data_timestamp в качестве ведущего столбца. Например:

WHERE data_timestamp >= '2015-12-18' 
    AND data_timestamp < '2015-12-18' + INTERVAL 1 DAY 

EXPLAIN выход для запроса с использованием шаблона LIKE покажет

type 
------ 
index 

Это показывает, что запрос может использовать индекс. Но он делает полную проверку индекса, глядя на каждую строку в индексе. Но гораздо более эффективный шаблон доступен. Мы можем позволить MySQL быстро устранить обширные ряды строк в индексе от рассмотрения, используя операцию сканирования диапазона. Запрос с предикатом, как во втором примере будет (должно) шоу:

type 
------ 
range 

Это собирается улучшить производительность запроса, который тянет относительно небольшое число строк из большого набора.


Больше пояснений, если я не прояснил это.Запись:

WHERE ts_col LIKE '2015-12-18%' 

фактически то же самое, как написание

WHERE CONVERT(ts_col,CHAR(18)) LIKE '2015-12-18%' 

И что заставляет MySQL выполнить операцию CONVERT по значению в ts_col для каждый строку в таблице.

ИТОГ

Не заставляйте ненужные преобразования типов данных столбцов из таблицы. Вместо этого сравните столбцы с их родными типами данных.

+0

Отличный отклик, он игнорировал индекс, это правильное решение (Использование выражения между операторами) Время выполнения запроса от 26 часов до 0,3 секунд – kevinn2065

+0

И единственный полезный индекс (для этого запроса, после изменения 'WHEREs'), является' INDEX (data_timestamp) '. –

+0

@Rick James: запрос OP может эффективно использовать * любой * индекс, который имеет 'data_timestamp' в качестве ведущего столбца. Коррелированный подзапрос может использовать индекс 'on (data_timestamp, first, last)'. Этот индекс будет индексом покрытия для подзапроса. Подзапрос может быть полностью удовлетворен из индекса без поиска страниц в базовой таблице. С созданием этого составного индекса индекс только для 'data_timestamp' будет избыточным. – spencer7593

0

Для этого запроса вам понадобится только ALTER TABLE tic_data add index (data_timestamp). Но data_timestamp должен быть CHAR или VARCHAR типа (вы сканируете его LIKE <string%>).

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