Конструкция if...else
в JavaScript решает массу различных задач, связанных с изменением хода алгоритма в зависимости от некоего условия. Однако за года существования JS в нем появилось много операторов и подходов к решения ряда задач с условиями. В этой статье мы рассмотрим такие интересные операторы и возможности языка JavaScript, как
- Тернарный оператор
- Присваивание значения по умолчанию при сравнении нескольких значений или переменных
- Оператор нулевого слияния
- Проверка объекта и свойства на существование
- Оператор опциональной последовательности
Тернарный оператор
Фактически тернарный оператор заменяет собой однострочную конструкцию if...else, когда и в ситуации, когда условие возвращает true
, и в ситуации, когда условие возвращает false
, нужно выполнить одно действие.
Записывается он следующим образом:
1 |
условие ? выражение_при_истинном_условии : выражение_при_ложном_условии |
Например, нам нужно выяснить, есть ли пользователю 18 лет. Используем для этого диалоговое окно confirm()
, которое после нажатия на кнопку "Ок" возвращает true
, а при нажатии на кнопку "Отмена" - false
. То есть такое диалоговое окно уже само по себе можно использовать в качестве условия, т.к. результатом проверки условия всегда является или true
, или false
.
1 2 3 4 5 6 7 8 9 10 |
// способ с if...else if (confirm("Вам уже есть 18 лет?")) alert("Приглашаем вас на триллер"); else alert("Предлагаем билеты на мультфильм"); // способ с тернарным оператором confirm("Вам уже есть 18 лет?") ? alert("Приглашаем вас на триллер"): alert("Предлагаем билеты на мультфильм"); //или ещё более краткая запись alert( confirm("Вам уже есть 18 лет?") ? "Приглашаем вас на триллер" : "Предлагаем билеты на мультфильм"); |
Такая запись очень наглядная и сразу даёт представление о том, что будет сделано в зависимости от выбора пользователя.
Протестируйте работу тернарного оператора, нажав на кнопку ниже.
Ещё один вариант использования тернарного оператора - это вывод каких-либо стилей в зависимости от действий пользователя. Например, от того, какое число ведёт пользователь, будет зависеть цвет абзаца или любого другого блока. Попробуйте сами.
Тестовы параграф. Если вы введете число меньше 50, он останется черным, если 50 и больше, станет красным. Жмите на кнопку быстрее и вводите число.
Код примера:
1 2 |
let num = +prompt("Введите произвольное число", "10"); parTest.style.color = num <50 ? "black" : "red"; |
Здесь parTest
- это id
нужного нам абзаца. Почему мы можем так к нему обратиться, описано в статье "Выбор элементов html-страницы с помощью JavaScript".
Присваивание значения по умолчанию при сравнении нескольких значений или переменных
В том случае, когда нам необходимо сравнить 2-3 переменных или 2-3 значения, одно из которых будет соответствовать false
, мы будем использовать логический оператор ИЛИ ||
. Результатом такого сравнения всегда будет первое значение, которое отлично от false
:
1 2 3 4 5 6 |
false || true // true false || "world" //"world " false || 1 //1 При сравнении чего-либо с false или undefined, всегда будет возвращаться значение, соответствующее true Первое из значений, возвращающихся true, будет результатом сравнения: false || 1 || 5; // 1 |
Используя логическое ИЛИ ||
, или другими словами оценку короткого замыкания OR(||)
, можно задать переменной значение по умолчанию в случае, когда переменная может иметь значение false
.
1 2 3 4 5 6 7 |
let defaultColor = "black"; let developerColor = undefined; let customColor = "orange"; let choosen = developerColor || defaultColor; console.log(choosen); // black choosen = customColor || defaultColor; console.log(choosen); // orange |
На этом принципе основан один из вариантов назначения параметров функции по умолчанию.
Оператор нулевого слияния
Оператор нулевого слияния записывается, как ??
, является нововведением в ES2020, и заменяет собой в какой-то степени логическое ИЛИ ||, если первое значение не определено.
Оператор нулевого слияния возвращает правую сторону, если левая сторона не определена (undefined
) или имеет значение null
. В противном случае он возвращает левую:
1 2 3 4 5 6 7 8 9 10 11 |
let index; // способ с if...else if(index){ console.log(index) } else { console.log("Индекс не указан") } // способ с оператором нулевого слияния console.log(index ?? "Индекс не указан"); |
То есть оператор нулевого слияния не оценивает значения 0, false
или пустую строку ''
, как достаточные для некоего значения по умолчанию. Вместо этого он использует только значения null
или undefined
- и все. В коде представлены несколько вариантов вывода различных значений при использовании этого оператора.
1 2 3 4 5 6 |
console.log(false || true);//true console.log(false ?? true);//false console.log(null ?? "word"); //word console.log("" ?? "word"); //<empty string> console.log(undefined ?? 12); //12 console.log(0 ?? 12); //0 |
Это удобно в том случае, если ваши объекты должны содержать ряд значений вида 0 или false
, например, но при этом вы их должны учитывать в коде именно в таком виде.
Проверка объекта и свойства на существование
Любой объект в JavaScript может существовать или отсутствовать на странице. Поскольку js-код часто пишется в одном файле для всего сайта, а не для отдельной странице, некоторые отсутствующие на данной странице элементы или другие объекты могут привести к ошибке в коде. Поэтому необходимо проверять сами объекты и их свойства на соответствие значениям null
(объект отсутствует) и undefined
(свойство не определено). Для этой цели можно использовать оценку короткого замыкания AND
(оператор &&
).
В примере ниже у нас явно задано, что объект pen
имеет значение null
. И если нам нужно проверить, есть ли в этом объекте свойство color
, необходимо использовать проверку с помощью оператора &&
:
1 2 3 |
const pen = null; const color = pen && pen.color; console.log(pen, color); //null null |
В том случае, если объект у нас определен, но нужное свойство отсутствует, проверка вернет undefined
:
1 2 3 4 5 6 |
const car = { model: "Ford Puma", maxVelocity: 180 } console.log(car.model, car.price); //Ford Puma undefined console.log(car.model && car.price); //undefined |
Еще один тест предназначен для работы с html-объектами на странице. Например, нам необходимо обратиться к элементу-изображению с id="myImage"
. Если оно есть на странице, то текст абзаца за ним с id="myText
" мы сделаем жирным, если нет - оставим без изменений.
Код примера с разметкой и скриптом:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
<img src="https://source.unsplash.com/1zR3WNSTnvY/400x300" alt="Test Image" id="myImage"> <p id="myText">Абзац для теста наличия изображения.</p> <button type="button" onclick="testImage()">Проверяем наличие изображения</button> <button type="button" onclick="deleteImage(this)">Удалить изображение</button> <script> function testImage() { let myImage = document.getElementById('myImage'), myText = document.getElementById('myText'); console.log(myText && myImage); myText.style.fontWeight = myText && myImage ? 'bold' : ''; } function deleteImage(btn) { myImage.remove(); btn.remove(); } </script> |
Сам пример для теста:
Абзац для теста наличия изображения.
До удаления изображения вы увидите в консоли ссылку на него, после удаления null
. Поскольку null
относится к одному из значений, соответствующему логическому false
, то использование тернарного оператора в строке 10 приведет к тому, что после удаления изображения условие вернет false
и жирное начертание для абзаца будет выключено.
Краткая запись вызова функции с использованием &&
Еще один пример связан с использованием функций. В том случае, когда вызов функции происходит в зависимости от переменной со значением true
, то можно применить оператор &&
как альтернативный вариант и более короткий вариант.
В примере ниже мы проверяем, доступно ли некое обновление вопросом к пользователю с помощью диалогового окна confirm()
и вызываем функцию setUpdate()
только в случае нажатия на кнопку ""Ок". Сравните вариант записи с if
и с оператором &&
.
1 2 3 4 5 6 7 8 9 10 11 12 |
function setUpdate(){ alert('Обновление устанавливается ...') } let isUpdate = confirm('Обновление доступно?'); // Обычная запись if (isUpdate ){ setUpdate(); } // Краткая запись isUpdate && setUpdate(); |
Давайте протестируем код:
Вот еще один пример, где мы обрабатываем массив объектов и выводим текст абзаца в зависимости от свойства объекта bodyOpen
с помощью оператор &&
. Тернарный оператор мы используем для отображения текста на кнопке и абзаца с текстом. Для последнего свойство display
принимает значение none
или block
в зависимости от свойства elemen.offsetHeight
:
See the Pen Operator && and Array.reverse() by Elen (@ambassador) on CodePen.
Оператор опциональной последовательности
В JavaScript достаточно часто приходится работать с объектами, особенно, если вы загружаете какую-либо информацию с сервера в формате JSON, например. Далеко не всегда у вас будет полная информация со всем набором свойств для каждого из объектов. В том случае, если вам надо получить доступ к свойству объекта с помощью оператора точки .
, а это свойство не определено (то есть отсутствует в списке свойств), то браузер выдаст ошибку, и дальнейший код работать не будет. Можно воспользоваться предыдущим подходом для определения наличия объекта или свойства, но еще интересней для этой цели использовать оператор опциональной последовательности.
Оператор опциональной последовательности записывается, как ?.
, то есть указываете знак ?
перед точкой доступа к любому свойству. Если такое свойство не определено, то вместо ошибки возвращается undefined
.
В примере ниже для первого объекта указаны все свойства, для второго отсутствует свойство person2.address.app
. Выполняем проверку 2-мя способами:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
const person1 = { name: "Игорь Матвеев", age: 35, address: { city: "Киев", street: "Л. Украинки, 22", app: 93 } }; const person2 = { name: "Ольга Иванова", age: 22, address: { city: "Харьков", street: "Клочковская", } }; // Способ с несколькими проверками console.log(person1 && person1.address && person1.address.app); // 93 console.log(person2 && person2.address && person2.address.app); //undefined // Способ с оператором опциональной последовтельности console.log(person1 ?.address ?.app); // 93 console.log(person2?.address?.app); // Не существует, возвращает undefined |
Почитать статью на английском с примерами.