SQL BETWEEN: включение диапазона чисел и дат

SQL BETWEEN фильтрует строки, где значение столбца попадает в заданный диапазон, включая обе границы. Он заменяет пару сравнений >= и <= одним предикатом, поэтому условия WHERE становятся короче, когда диапазон должен быть включающим. BETWEEN работает с числами, датами и текстом, но для диапазонов дат нужно учитывать компоненты времени.

Пример SQL BETWEEN Для Фильтрации По Диапазону

Вывод:

Результат появится здесь...

Вывод:

+----------+-------+------------+
| customer | total | placed     |
+----------+-------+------------+
| Ben      | 120.5 | 2026-02-15 |
| Cara     | 89.99 | 2026-02-20 |
+----------+-------+------------+
2 row(s)

Как Работает Этот Пример

  1. CREATE TABLE и INSERT создают таблицу orders с четырьмя строками, где суммы и даты лежат в разных диапазонах.
  2. WHERE total BETWEEN 50 AND 150 оставляет только строки, где total >= 50 AND total <= 150. Обе границы включены, поэтому строка с ровно 50 или 150 тоже подойдет.
  3. Строки с суммами 45.00 и 200.00 выходят за диапазон и исключаются.

x BETWEEN y AND z эквивалентно x >= y AND x <= z. Если одна из границ равна NULL, предикат вычисляется в unknown, и строка отфильтровывается.

Что Такое SQL BETWEEN?

SQL BETWEEN проверяет, попадает ли значение во включающий диапазон: column >= low AND column <= high. Для числовых диапазонов запись читается проще и ведет себя предсказуемо. Некоторые СУБД также поддерживают BETWEEN SYMMETRIC, который меняет границы местами, если они переданы в обратном порядке.

Частые Ошибки С SQL BETWEEN

Ошибка: Использовать BETWEEN для диапазонов timestamp.

Неправильно:

WHERE placed BETWEEN '2026-02-01' AND '2026-02-28'

Правильно:

WHERE placed >= '2026-02-01' AND placed < '2026-03-01'

Почему это происходит: если столбец хранит время, конечная дата вроде '2026-02-28' обычно совпадает только с началом этого дня. Используйте полуоткрытый интервал, чтобы захватить весь день.

Ошибка: Поменять границы местами и ожидать результат.

Неправильно:

WHERE total BETWEEN 150 AND 50

Правильно:

WHERE total BETWEEN 50 AND 150

Почему это происходит: в обычном BETWEEN первая граница должна быть нижней. Если границы перепутаны, условие не может стать истинным.

BETWEEN vs IN vs Операторы Сравнения

ПодходКогда использовать
BETWEEN low AND highДиапазон непрерывный, и обе границы включены
>= low AND < highНужна исключающая верхняя граница (timestamp, пагинация)
IN (a, b, c)Значения дискретные, а не непрерывный диапазон
> low AND < highОбе границы должны быть исключающими

Правило: для включающих числовых диапазонов обычно лучше BETWEEN. Переходите к явным сравнениям, когда одна граница должна быть исключающей, особенно для дат. Используйте IN для фиксированного набора значений; BETWEEN в таком случае захватит нежелательные значения в промежутках.

Заметки О Производительности

BETWEEN является sargable, планировщик запросов обрабатывает его как >= AND <= и может использовать B-tree индекс по фильтруемому столбцу. Обертка столбца функцией (DATE(col), LOWER(col)) блокирует использование индекса; лучше нормализовать границы. Широкие диапазоны все равно читают много строк даже с индексом, поэтому селективность важнее выбора оператора.

FAQ

SQL BETWEEN включает границы или исключает их?

BETWEEN включает обе границы. WHERE x BETWEEN 5 AND 10 возвращает строки, где x равен 5, 6, 7, 8, 9 или 10. Встроенного исключающего варианта нет, для этого используйте > и <.

Можно ли использовать BETWEEN с текстовыми значениями?

Да. WHERE name BETWEEN 'A' AND 'M' возвращает имена, которые сортируются в этом диапазоне при текущей коллации. Результат зависит от правил сортировки и чувствительности к регистру в вашей СУБД, поэтому перед продакшеном это лучше проверить в вашей конфигурации.

Почему BETWEEN пропускает записи на конечной дате?

Когда столбец хранит datetime (дата + время), верхняя граница вроде '2026-02-28' часто трактуется как начало этого дня. Любая строка позже этого момента 28 февраля окажется за пределами диапазона. Используйте полуоткрытый интервал (>= start AND < next_day), чтобы захватить весь день.