Комментарии 18
занятно, можно еще упомянуть о проблемах разруливания индексов.
когда в запросе используется один индекс, а в order by другой, то мускул тупит и не может решить какой индекс брать, нужно подсказывать use index.
когда в запросе используется один индекс, а в order by другой, то мускул тупит и не может решить какой индекс брать, нужно подсказывать use index.
да, согласен, а ещё когда count считаешь он pk подхватывает и сканит всю таблицу, ибо innodb, вместо какого-нибудь другого индекса меньшего по размеру.
если бы я описал все что хотел, боюсь это точно никто не стал бы читать.
к сожалению пришлось отрезать много интересного материала
если бы я описал все что хотел, боюсь это точно никто не стал бы читать.
к сожалению пришлось отрезать много интересного материала
ну как бы вроде это не проблема — разбиваем статью на несколько частей, и постим.
афаик, это из-за особенностей реализации вторичных ключей в иннодб — для вторичных он делает лукап в первичном, поэтому скан втотричного индекса всегда медленее чем первичного, даже если вторичный в разы меньше первичного.
Не советую так делать (скажу даже резче — не в коем случае), когда надо использовать другой индекс поверьте мускул затупит еще больше.
Тормоза будут гораздо больше.
Лучше все же оптимизировать, проверить несколько вариантов использования индексов.
Лучше, что называется предложить ему пару вариантов для использования индексов.
Поверьте мускул не такой тупой он вернее найдет нужный индекс, просто ему нужно немного оптимизировать бд и запрос. :)
Тормоза будут гораздо больше.
Лучше все же оптимизировать, проверить несколько вариантов использования индексов.
Лучше, что называется предложить ему пару вариантов для использования индексов.
Поверьте мускул не такой тупой он вернее найдет нужный индекс, просто ему нужно немного оптимизировать бд и запрос. :)
практика и теория показывают другое :)
dev.mysql.com/doc/refman/5.5/en/order-by-optimization.html
увы у меня никак не получилось придумать как переделать по-другому запрос:
SELECT * FROM t1 WHERE key2 = constant ORDER BY key1;
кроме как явно указать какой индекс использовать.
dev.mysql.com/doc/refman/5.5/en/order-by-optimization.html
увы у меня никак не получилось придумать как переделать по-другому запрос:
SELECT * FROM t1 WHERE key2 = constant ORDER BY key1;
кроме как явно указать какой индекс использовать.
Возьмет тот индекс, по которому быстрее выборка, в зависимости от контента таблицы, главное не мешайте. А теперь поставим задачу более обширную, когда в своей системе вы например решили добавить фитчу добавления полей, отсюда вылезет join, и в зависимости от наполнения и индексов, mysql сам решит что брать (правда все равно не мешает перед этим explain-ом пошерстить), а если у вас будет индекс задан явно — ждите тормозов.
Очень редко встречал когда кто-то задает use index, всегда можно оптимизировать или запрос или структуру или архитектуру.
Очень редко встречал когда кто-то задает use index, всегда можно оптимизировать или запрос или структуру или архитектуру.
вы по ссылке не читали?
«In some cases, MySQL cannot use indexes to resolve the ORDER BY, although it still uses indexes to find the rows that match the WHERE clause»
Будет использовать всегда в том запросе key2, хотя key1 может быть гораздо эффективнее.
«In some cases, MySQL cannot use indexes to resolve the ORDER BY, although it still uses indexes to find the rows that match the WHERE clause»
Будет использовать всегда в том запросе key2, хотя key1 может быть гораздо эффективнее.
хм… я вообще то всегда думал, что эта проблема решается созданием составного индекса.
то, что MySQL не умеет грамотно опеределять какой именно индекс использовать в запросе, это и ежу понятно, и именно по этому необходимо разруливать такие случаи самостоятельно, а решение с явным указанием индекса всегда будет наихудшим, ибо может перестать работать. когда гистограмма распределения станет другой, или появятся дополнительный колонки в таблице. Оно просто иллюстрирует, что если у вас значения индекса, который используется в условии WHERE, не является высокоселективным, то алгоритмы использемые MySQL для оптимизации в этом случае явно далеки от идеала, и с этим надо бороться. Просто надо бороться, а как это уже другой вопрос, который в каждой конкретной ситуации надо решать своим способом.
то, что MySQL не умеет грамотно опеределять какой именно индекс использовать в запросе, это и ежу понятно, и именно по этому необходимо разруливать такие случаи самостоятельно, а решение с явным указанием индекса всегда будет наихудшим, ибо может перестать работать. когда гистограмма распределения станет другой, или появятся дополнительный колонки в таблице. Оно просто иллюстрирует, что если у вас значения индекса, который используется в условии WHERE, не является высокоселективным, то алгоритмы использемые MySQL для оптимизации в этом случае явно далеки от идеала, и с этим надо бороться. Просто надо бороться, а как это уже другой вопрос, который в каждой конкретной ситуации надо решать своим способом.
Ох. Добавил в избранное, буду читать на свежую голову. Уставшая что-то отказывается понимать.
Статья получилась интересная, вот интересно откуда картинки брали? сами нарисовали?
Изначально рисунков не планироволось вообще, но так как без них получилось бы очень много текста, который надо внимательно читать, чтобы понять суть, то я решил перенести его в иллюстрации. Так визуально легче. Естественно рисовать их пришлось с ноля. Жаль хабр эффект не воспринимает svg, так бы я прям исходниками его выложил, в векторе.
Ох, вот по моему мнению, вместо того, чтобы городить страшные процедуры и разбираться во всем этом, проще на уровне приложения сделать 2 выборки и сджойнить. Ну и, если есть такая возможность, денормализовать данные или что-то поменять, может и без джойна обойтись можно будет. А то никаких гарантий, что завтра в MySQL поменяется логика работы планировщика и все это перестанет работать, как я понимаю, нету.
Спасибо за статью. Почерпнул для себя много полезного. И за иллюстрации еще одно спасибо — так информация воспринимается гораздо лучше.
«Если у тебя в рукаве козырной туз в виде Oracle, то есть шанс, что эти костыли он подставит сам.»
К сожалению, шанс совсем не велик.
Сколько приходилось переписывать всякие селекты, когда переупорядочевание условий в where может менять скорость работы.
Еще и их так называемые хинты, без которых тоже плохи дела.
А еще и вложенные запросы, когда в некоторых обстоятельствах результат не кешируется до конца выполнения всего запроса, и раз за разом повторяется, увеличивая время выполнения.
Так что, Оракл это не такой уж козырь.
К сожалению, шанс совсем не велик.
Сколько приходилось переписывать всякие селекты, когда переупорядочевание условий в where может менять скорость работы.
Еще и их так называемые хинты, без которых тоже плохи дела.
А еще и вложенные запросы, когда в некоторых обстоятельствах результат не кешируется до конца выполнения всего запроса, и раз за разом повторяется, увеличивая время выполнения.
Так что, Оракл это не такой уж козырь.
Зарегистрируйтесь на Хабре, чтобы оставить комментарий
Как MySQL оптимизирует ORDER BY, LIMIT и DISTINCT