Преимущества запросов на обновление MySQL от индекса? - PullRequest
19 голосов
/ 21 июля 2011

У меня есть таблица, которую я в основном обновляю, и мне интересно, выиграют ли запросы обновления от наличия индекса для столбца where и обновленного столбца или индекса только для столбца where?

Ответы [ 3 ]

18 голосов
/ 21 июля 2011

Просто на колонке где. Индекс в столбце обновления фактически замедлит ваш запрос, потому что индекс должен обновляться вместе с данными. Индекс столбца where ускоряет обновления и выбирает, но замедляет некоторые вставки.

Индексы также вызывают накладные расходы при удалении строк. В целом, это хорошая вещь, хотя для столбцов, которые вы используете WHERE для большого количества, и они в основном необходимы для столбцов, к которым вы присоединяетесь, или ORDER BY

13 голосов
/ 21 июля 2011

Большинство людей здесь не знают, как работают индексы в MySQL.

Это зависит от используемого вами механизма хранения . InnoDB использует индексы, полностью отличающиеся от MyISAM. Это связано с тем, что MySQL реализует индексы на уровне механизма хранения , а не на уровне сервера MySQL.

Боюсь, что большинство людей здесь дают вам ответы на основе других баз данных, в которых индексы работают иначе по сравнению с MySQL.

InnoDB

В случае InnoDB. Это происходит потому, что всякий раз, когда строка обновляется в InnoDB, индекс также должен обновляться, так как индексы InnoDB's должны быть последовательными, поэтому он должен выяснить, в каком узле страницы индекса он должен находиться. и вставил туда. Иногда эта конкретная страница может быть заполнена, поэтому приходится разбивать страницу , тратя впустую пространство и увеличивая время. Это происходит независимо от того, какой столбец вы индексируете, потому что InnoDB использует кластерные индексы, где индекс хранит данные всей строки.

MyISAM

В случае MyISAM у него нет этой проблемы. MyISAM на самом деле использует только 1 индекс столбца, хотя вы можете установить несколько уникальных значений для более чем 1 столбца. Также индекс MyISAM's не сохраняется последовательно, поэтому обновления выполняются очень быстро. Точно так же вставки выполняются быстро, так как MyISAM просто вставляет его в конец строки.

Заключение

Итак, что касается вашего вопроса, вы должны рассмотреть проект схемы, а не беспокоиться о том, будет ли запрос использовать индексы. Если вы обновляете в основном таблицы, я советую вам не использовать InnoDB, если только вам не нужна блокировка на уровне строк, высокий уровень параллелизма и транзакции. В противном случае MyISAM будет гораздо лучше для задач обновления. И нет, если вы используете InnoDB, индексы не очень помогают с обновлением, особенно если таблица очень большая.

8 голосов
/ 21 июля 2011

Не прямой ответ на этот вопрос.Итак, вот так.

UPDATE table SET ColumnA = 'something' 

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

UPDATE table SET ColumnA = 'something' WHERE ColumnB = 'something else'

Для этого запроса, если индекс существует для ColumnB, а не для ColumnA, будет очень быстро найти запись (называемую поиском) и одну запись для обновления, и, так как индекс не заботится о columnA, ему не понадобитсяОбновление.
Но если вы индексируете ColumnA, а не ColumnB, сначала вы будете читать каждую строку в таблице (это называется сканированием и, как правило, плохим), который, хотя чтение выполняется быстрее, чем запись, все еще очень медленный, а затемзапишет в таблицу, а затем еще одну запись для индекса.В основном самый медленный способ сделать это.

DELETE table WHERE ColumnB = 'somethingelse'

Теперь, если у вас есть индекс для любого столбца в этой таблице, две записи, удаление из таблицы и обновление / удаление записи в индексе.
Опять же, если ColumnB не проиндексирован, вы сканируете таблицу, затем удаляете строки из таблицы и обновляете индексы, если таковые имеются.

INSERT INTO table (ColumnA, ColumnB) VALUES ('something','something else')

Если индексов не существует, выполняется одна запись в таблицу, и онаготово.
Опять же, если индексы существуют, то для каждого из них требуется дополнительная запись.

Я не упомянул ограничения уникальности первичного ключа, потому что вы действительно не можете обойти их, когда вам нужен первичный ключ, но каждая запись должна быть проверена, чтобы увидеть, существует ли что-то с этим ключом перед вставкой.Это будет быстрый поиск по первичному ключу, но, тем не менее, это еще один шаг в этом процессе.Чем меньше шагов, тем быстрее это будет.

Теперь вернемся к вашему. В принципе, если вам нужно обновить определенную запись, индекс поможет вам найти эту запись быстрее, чем сканировать всю таблицу.Время, сэкономленное на поиске записи, будет намного больше, чем время, потраченное на обновление индексов.Если вы только вставляете и никогда не читаете, то индексы замедлят вас.Это становится балансом.Если вам нужно прочитать конкретные записи, то очень поможет индекс.Но чем больше индексов, тем медленнее становится запись.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...