Размер индекса InnoDB с разрешенными значениями NULL (MySQL) - PullRequest
0 голосов
/ 25 ноября 2018

Интересно, нашел ли кто-нибудь подтверждение в документации по MySQL, что для InnoDB столбец, который допускает значение NULL в индексе, занимает 1 дополнительный байт?

Пример: создать столбец SMALLINT UNSIGNED DEFAULT NULL; (2 байта).Индекс использует 3 байта (без учета PK-ссылок).

Тот же столбец, который не допускает NULL: SMALLINT UNSIGNED NOT NULL;Индекс будет таким, каким он должен быть - 2 байта.

UPD: я нашел это в документах: «Из-за формата хранения ключей длина ключа на один больше для столбца, который может быть NULL, чем для NOTNULL столбец. "Но, тем не менее, я не понимаю, будет ли размер индекса на 1 байт больше для столбца NULLable или нет.

PS Извините за мой плохой английский:)

1 Ответ

0 голосов
/ 25 ноября 2018

Есть несколько недостатков в key_len из EXPLAIN.

  • Есть различия между двигателями, но Explain не учитывает такие.
  • Нулевой битможет или не может занять полный байт.Тем не менее, 3 против 2 - это удобная подсказка, что SMALLINT равно NULL или NOT NULL.
  • VAR... на самом деле занимает переменное количество места.
  • InnoDB` имеет1- или 2-байтовый префикс для каждого столбца;это не упомянуто.
  • key_len обычно учитывает любые столбцы, которые были протестированы с =.Если есть также тест «диапазона» (BETWEEN, >, LIKE 'foo%', etc), который может использовать часть индекса, key_len не указывает на такое.
  • То же самое для использования части индекса для GROUP BY и ORDER BY.

Вы можете получить больше информации (но не «все»), используя EXPLAIN FORMAT=JSON SELECT ....

Логически, если не в действительности , в 2-байтовом SMALLINT нет места для NULL. Таким образом, требуется больше места - хотя бы один бит.

Есть две отдельные проблемы- Размер индекса BTree и структуры данных, использованных во время запроса.

Я бы сказал, что не стоит беспокоиться о дополнительном байте или бите для NULL.лучше сказать NOT NULL за исключением случаев, когда у вас есть требование "бизнес-логики" для NULL (без значения, N / A, еще не указано, и т. д. и т. д.). Затем пусть таблица, индекс и т. д. потребляют дополнительный битили байт при необходимости.

Я думаю (без достаточного подтверждения), что InnoDB не занимает дополнительное место для нулевого бита - это один из 8 или16 битов с префиксами каждого столбца.

Обратите внимание, что в InnoDB индекс BTree по существу идентичен данным BTree.(И PRIMARY KEY - это порядок данных BTree.)

...