Update:
Посмотреть эту запись в моем блоге подробности производительности:
SELECT * FROM table WHERE field & number = number
SELECT * FROM table WHERE field | number = number
Этот показатель может быть эффективным двумя способами:
- Чтобы избежать раннего сканирования таблицы (так как значение для сравнения содержится в самом индексе)
- Для того, чтобы ограничить диапазон значений рассмотренных.
Ни условие в запросах выше sargable, это индекс не будет использоваться для сканирования диапазона (с условиями, как сейчас).
Однако точка 1
по-прежнему сохраняется, и индекс может быть полезен.
Если ваша таблица содержит, скажем, 100
байт в строке в среднем и 1,000,000
записей, то сканирование таблицы необходимо будет сканировать 100 Mb
данных.
Если у вас есть индекс (с ключом 4
-байта, 6
-байтом указателя строки и некоторыми внутренними накладными расходами), запросу нужен будет сканировать только 10 Mb
данных плюс дополнительных данных из таблицы, если фильтр успешно.
- Сканирование таблицы более эффективно, если ваше состояние не является выборочным (у вас есть высокая вероятность соответствовать условию).
- Сканирование индекса более эффективно, если ваше условие является выборочным (у вас низкая вероятность соответствовать условию).
Оба этих запроса потребуют сканирования всего индекса.
Но, переписывая запрос AND
, вы также можете воспользоваться ранжированием по индексу.
Это условие:
field & number = number
может соответствовать только поля, если высшие биты number
набора установлены в field
тоже.
И вы должны просто предоставить это дополнительное условие для запроса:
SELECT *
FROM table
WHERE field & number = number
AND field >= 0xFFFFFFFF & ~((2 << FLOOR(LOG(2, 0xFFFFFFFF & ~number))) - 1)
Это будет использовать диапазон для грубой фильтрации и условия для тонкой фильтрации.
Чем больше бит для number
не установлено в конце, тем лучше.
Это отличный вопрос, но вам нужно принять некоторые из ваших ответов - 20% не собираются приглашать людей, чтобы попытаться ответить на него. – Fragsworth