switch: выбор по точному значению
В переменной size – размер одежды: одна из строк 'XS', 'S', 'M'. Для каждого значения нужно вывести свою подпись – три точных значения, три ответа. Через if..else получается цепочка:
const size = 'M';if (size === 'XS') { console.log('очень маленький');} else if (size === 'S') { console.log('маленький');} else if (size === 'M') { console.log('средний');} else { console.log('такого размера нет');}Работает, но читается тяжело: три раза повторяется переменная, три раза – оператор ===, а различаются ветки только значением в скобках. Когда одно значение нужно сверить с перечнем точных вариантов, в языке есть отдельная конструкция – switch. Вот та же задача в новой записи:
const size = 'M';switch (size) { case 'XS': console.log('очень маленький'); break; case 'S': console.log('маленький'); break; case 'M': console.log('средний'); break; default: console.log('такого размера нет');}Разберём запись. В круглых скобках после слова switch стоит выражение – здесь это переменная size. В фигурных скобках – тело: ветки case. Каждая начинается строкой вида case 'XS': – слово case, значение, двоеточие, – а ниже идёт код ветки. Работает это так:
- Выражение в скобках вычисляется – один раз.
- Его результат сравнивается со значением каждого
caseсверху вниз. Сравнение – строгое===: без приведения типов. - Нашлось совпадение – выполнение начинается с этой ветки и идёт до
break, который завершаетswitch. - Не совпал ни один
case– выполняется веткаdefault. Если её нет, не срабатывает ни одна ветка: выполнение продолжается с кода после закрывающей скобкиswitch.
Этот проход по шагам:
size – строка 'M'.const size = 'S';switch (size) { case 'XS': console.log('очень маленький'); case 'S': console.log('маленький'); case 'M': console.log('средний'); default: console.log('такого размера нет');}Здесь ни в одной ветке нет break – и в консоли три строки вместо одной. case задаёт только точку входа, а не отдельную ветку: выполнение начинается с совпавшего case и без break просто течёт вниз, через все следующие ветки. Это называют проваливанием. Заметьте: case 'M' и default выполнились, хотя значение 'S' с ними не сравнивалось – сравнение закончилось на точке входа.
Поэтому break ставят в конце каждой ветки. В последней он формально не нужен, но его пишут тоже: ветка, дописанная ниже, ничего не сломает.
size – 'S', и ни в одной ветке нет break.Когда совпадения нет
default подхватывает несовпавшие значения; сравнение с case строгое – тип важен.
default: ни один не совпал
const size = 'XL';switch (size) { case 'XS': console.log('очень маленький'); break; case 'S': console.log('маленький'); break; case 'M': console.log('средний'); break; default: console.log('такого размера нет');}В переменной size теперь значение 'XL': оно не совпало ни с одним case – выполнилась ветка default. Она подхватывает все значения, которых нет в перечне, и обычно стоит последней: читается как «все остальные случаи». Ветка не обязательна: без default несовпавшее значение просто ничего не запустит, и программа продолжится после switch.
Сравнение строгое: тип важен
// значение из поля ввода – строкаconst input = '2';switch (input) { case 1: console.log('первый'); break; case 2: console.log('второй'); break; default: console.log('вариант не найден');}Строка '2' не совпала с числом 2: case сравнивает строго, без приведения типов – сработал default. Тип важен: данные из полей ввода приходят строками, и переводить их в число нужно до сравнения.
В скобках switch при этом может стоять не только переменная, а любое выражение – оно вычислится один раз, и сравниваться будет его результат:
const input = '2';// выражение: строка переведена в числоswitch (Number(input)) { case 1: console.log('первый'); break; case 2: console.log('второй'); break; default: console.log('вариант не найден');}const status = 'shipped';switch (status) { case 'paid': case 'shipped': console.log('заказ в работе'); break; case 'delivered': console.log('заказ завершён'); break; default: console.log('неизвестный статус');}У case 'paid': нет своего тела – выполнение проваливается вниз, до общего кода: «заказ в работе» печатается и для 'paid', и для 'shipped'. Несколько case подряд – несколько точек входа в одну ветку.
Такое проваливание между case намеренное и пустое: между сгруппированными case ничего не пишут.
const key = 'ArrowUp';switch (key) { case 'w': case 'ArrowUp': console.log('вверх'); break; case 's': case 'ArrowDown': console.log('вниз'); break;}'w', и стрелка 'ArrowUp' ведут в общую ветку. default не нужен: прочие клавиши ничего не делают.if..else или switch: что выбрать
Перечень точных значений – switch; диапазоны и составные условия – if.
Инструменты пересекаются, и выбор между ними – про читаемость. switch уместен в одном сценарии: одна переменная сравнивается с перечнем точных значений – коды, размеры, названия команд. Перечень читается как таблица, и добавить вариант – одна ветка.
if..else – инструмент общего назначения, и он единственный выбор, когда условия – диапазоны (score >= 90), разные переменные или составные проверки с &&: в case такое не записать, он сравнивает только на строгое равенство.
На практике if..else встречается заметно чаще. Если сомневаетесь – начинайте с него, а на switch переходите, когда цепочка else if (x === ...) по одной переменной разрослась.
const lang = 'ru';// перечень точных значений одной переменной – удобен switch:switch (lang) { case 'ru': console.log('Привет'); break; case 'en': console.log('Hello'); break; default: console.log('нет перевода');}const age = 20;const hasTicket = true;// диапазоны и составные условия – только if:if (age >= 18 && hasTicket) { console.log('проходите');}// теперь вы знаете
- В скобках switch – любое выражение: оно вычисляется один раз, дальше сравнивается результат
- case – точка входа: без break выполнение проваливается вниз по веткам
- default подхватывает несовпавшие значения; без него несовпавшее значение просто ничего не запускает
- Сравнение с case – строгое
===: строка '2' не совпадёт с числом 2 - Несколько case подряд без тела – группировка: несколько входов в общий код
- switch – для перечня точных значений; диапазоны и составные условия – if
Из switch убрали оба break. Что попадёт в консоль при size = 'M'?
const size = 'M';switch (size) {case 'S':console.log('маленький');case 'M':console.log('средний');default:console.log('такого размера нет');}
Что попадёт в консоль?
const value = 1;switch (value) {case '1':console.log('совпало');break;default:console.log('не совпало');}