Сосредоточив внимание на диапазоне дат, MySQL в основном имеет две опции:
последовательно прочитать всю таблицу и выбросить записи, которые не соответствуют диапазону дат
использовать индекс для идентификации записей в диапазоне дат, а затем искать каждую запись в таблице (используя первичный ключ) в отдельности («произвольный доступ»)
Последовательное чтение значительно быстрее, чем произвольный доступ, но вам нужно прочитать больше данных. Будет некоторая точка безубыточности, при которой использование индекса станет медленнее, чем простое чтение всего, и MySQL предполагает, что это так. Если это правильный выбор, во многом зависит от того, насколько правильно он угадал, сколько записей на самом деле находится в диапазоне. Если вы сделаете диапазон меньше, он должен использовать индекс в какой-то момент.
Если вы знаете, что (или хотите проверить, быстрее ли) использовать индекс, вы можете заставить MySQL использовать его с
... FROM TAS_USAGE t1 force index (last_quarter) LEFT JOIN ...
Вам следует протестировать его с разными диапазонами, и если вы генерируете свой запрос динамически, форсируйте индекс только тогда, когда вы достаточно уверены (поскольку MySQL не исправит вас, если, например, вы укажете диапазон, включающий все строки).
Существует один важный способ обойти медленный произвольный доступ к таблице, хотя, к сожалению, он не работает с вашим префиксным индексом, но я упомяну об этом в случае, если вы можете уменьшить размеры полей (или изменить их на поиски / перечисления). Вы можете включить каждый столбец, который необходим MySQL для оценки запроса, используя индекс покрытия :
Индекс, который включает в себя все столбцы, полученные по запросу. Вместо того чтобы использовать значения индекса в качестве указателей для поиска полных строк таблицы, запрос возвращает значения из структуры индекса, сохраняя дисковый ввод-вывод.
Как уже упоминалось, поскольку в префиксном индексе часть данных отсутствует, эти столбцы, к сожалению, нельзя использовать для покрытия.
На самом деле их вообще нельзя использовать вообще, особенно, чтобы не фильтровать записи перед выполнением произвольного доступа, так как для оценки вашего where
-условия для RUNSTATUS
или SERVICE
, в любом случае требуется полное значение , Таким образом, вы можете проверить, например, RUNSTATUS
очень важно - возможно, 99% ваших записей находятся в статусе «Сбой» - и в этом случае добавьте фильтр без префикса для просто
(SERVERTIME, RUNSTATUS)
(и MySQL может даже выбрать этот индекс самостоятельно).