Есть несколько недостатков в 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.)