Возможно ли иметь функциональный индекс в MySQL?
Я вспоминаю в Oracle, что можно индексировать на основе функции, например. SUBSTRING(id,1,8)
.
Поддерживает ли MySQL это? Если нет, есть ли альтернатива?
Ответы
Ответ 1
Нет, не в общем смысле, я не верю, что даже 5.6 (последняя версия, когда этот ответ был впервые написан) обладает такой функциональностью. Стоит отметить, что 8.0.13 и выше теперь поддерживают функциональные индексы, что позволяет вам достичь того, что вам нужно, без метода триггера, описанного ниже.
См. Https://dev.mysql.com/doc/refman/8.0/en/create-index.html для получения более подробной информации об этом.
Если вы работаете с более старой версией mysql
, можно использовать только начальную часть столбца (эта функция существует уже давно), но не одну, начинающуюся со второго или последующих символов, или любую другую, более сложную. функция.
Например, следующее создает индекс, используя первые пять символов имени:
create index name_first_five on cust_table (name(5));
Для более сложных выражений вы можете добиться аналогичного эффекта, имея другой столбец с индексируемыми данными в нем, а затем используя триггеры вставки/обновления, чтобы обеспечить его правильное заполнение.
Кроме потерянного пространства для избыточных данных, это почти то же самое.
И, хотя это технически нарушает 3NF, это смягчается использованием триггеров для синхронизации данных (это часто делается для повышения производительности).
Ответ 2
MySQL не поддерживает это, но есть альтернатива.
1. Поскольку MySQL 5.7.6
Вы можете использовать автоматически созданный столбец для хранения подстроки с индексом на ней:
CREATE TABLE SomeTable (
id CHAR(10),
sub_id CHAR(8) AS SUBSTRING(id, 1, 8) STORED, INDEX(sub_id)
)
Как отметил Benjamin, InnoDB поддерживает вторичные индексы на виртуальных столбцах, поэтому ключевое слово STORED можно опустить. Фактически, вторичные индексы на виртуальных столбцах могут быть предпочтительнее. Подробнее здесь: Вторичные индексы и созданные столбцы
2. Перед MySQL 5.7.6
Вы можете использовать столбец, обновленный триггером с индексом на нем:
CREATE TABLE SomeTable (
id CHAR(10),
sub_id CHAR(8) , INDEX(sub_id)
);
CREATE TRIGGER TR_SomeTable_INSERT_sub_id
BEFORE INSERT
ON SomeTable FOR EACH ROW
SET NEW.sub_id = SUBSTRING(NEW.id, 1, 8);
CREATE TRIGGER TR_SomeTable_UPDATE_sub_id
BEFORE UPDATE
ON SomeTable FOR EACH ROW
SET NEW.sub_id = SUBSTRING(NEW.id, 1, 8);
Ответ 3
Это возможно с MySQL 5.7.5 с использованием нового Созданных столбцов.
Ответ 4
Да, мы можем создать функциональный индекс в MySQL. Эта функция доступна в MySQL 8.0.13. (Другие СУБД имеют эту функцию в более ранних выпусках, но MySQL представила ее в своем выпуске 8.0.13). Функциональный индекс
Здесь я привел пример для создания функционального индекса в MySQL8.0
Это запрос
выберите * в app_user, где month (creationOn) = 5;
mysql> select * from app_user где month (creationOn) = 5; 7e9e2b7bc2e9bde15504f6c5658458ab - 74322 строки в наборе (5,01 с)
Он выполняет более 5 секунд для получения 74322 записей, даже если у меня есть индекс для столбца созданного на. (Индексирование на столбце созданного на не оптимизатором не используется, так как он маскируется функцией month())
Теперь я создал функциональный индекс для столбца, используя следующий синтаксис.
mysql> изменить таблицу app_user добавить индекс idx_month_createdon ((month (creationOn))); Запрос в порядке, затронуто 0 строк (1 мин. 17,37 с). Записи: 0 Дубликаты: 0 Предупреждения: 0
mysql> select * from app_user где month (creationOn) = 5; 7e9e2b7bc2e9bde15504f6c5658458ab - 74322 строки в наборе (0,29 с)
После создания функционального индекса он выполняется за 0,29 с.
На веб-сайте Mysql трудно найти документ с указанием функционального индекса, он назван в виде функциональных ключевых частей.
И мы не можем отбросить столбец, имеющий функциональный индекс. Чтобы достичь, нам нужно отбросить функциональный индекс в первую очередь.
mysql> изменить таблицу app_user отбрасывать столбец созданныйOn; Невозможно удалить столбец createOn, поскольку он используется функциональным индексом. Чтобы удалить столбец, необходимо удалить функциональный индекс.
Если вы используете MySQL> 5.7.5, вы можете добиться того же, используя сгенерированные столбцы.
Ответ 5
Да, мы можем создать функциональный индекс в MySQL. Эта функция доступна в MySQL 8.0.13. (Другие СУБД имеют эту функцию в более ранних выпусках, но MySQL представила ее в своем выпуске 8.0.13). Функциональный индекс
Если вы используете MySQL> 5.7.5, вы можете добиться того же, используя сгенерированные столбцы.