JavaScript  —  хороший язык, но меня он часто озадачивает.

Может, я недостаточно его знаю, но иногда просто не понимаю, как тут все устроено.

Сможете правильно ответить на непростые вопросы ниже?

1. Почему и в false == [], и в false == ![] возвращается true?

Как ни странно, это действительно так.

Разберемся, применив знания о сравнениях на равенство и тождественности.

console.log(false == []) // true
console.log(false == ![]) // true

Для окончательного сравнения и логическое значение, и объект преобразуются в числа.

Вот этапы сравнения:

// 1. false преобразуется в число, чтобы получить 0
// 2. [] преобразуется в число, чтобы получить 0
// 3. При "0 == 0" возвращается true
console.log(false == []) // true
// 1. Результат выполнения "![]" - false
// 2. При false == false возвращается true
console.log(false == ![]) // true

2. Почему в [] == ![] возвращается true?

Каков результат 1 == !1? Что возвращается в ‘fatfish’ == !’fatfish’?

Что особенного в пустых массивах?

// 1. Результат выполнения "![]" — false
// 2. Сравнивается "[] == false"
// 3. [] преобразуется в число, чтобы получить 0
// 4. false преобразуется в число, чтобы получить 0
// 5. При "0 == 0" возвращается true

console.log([] == ![])

С === работать намного проще, а с == возможны кошмары.

3. О странном try catch

А что возвращается при выполнении getName  —  fatfish или medium?

const getName = () => {
try {
return 'fatfish'
} finally {
return 'medium'
}
}
getName() // ?

fatfish? А вот и нет! medium.

В конструкции try… .catch… .finally оператор finally выполняется независимо от того, выбрасывается ли исключение или нет. А если выбрасывается, конструкция в операторе finally выполняется, даже если нет оператора catch для обработки исключения.

4. О стрелочной функции

Это очень просто: выводится fatfish:

const fn = () => 'fatfish'

console.log(fn()) // fatfish

Но что выводится в этом коде?

const fn = () => {}

console.log(fn()) // ?

Думаете, {}?

{}  —  это блок, в котором находится функция fn, поэтому:

const fn = () => {
}

console.log(fn()) // undefined

Хотя, если возвращать объект  —  пустой или непустой  —  из стрелочной функции, не используя ключевое слово return, должно быть так:

const fn = () => ({})

console.log(fn()) // {}

5. Почему JSON.stringify(‘fatfish’) ! == ‘fatfish’?

name1 эквивалентно name2?

const name1 = JSON.stringify('fatfish')
const name2 = 'fatfish'

console.log(name1 === name2) // ?

Нет. Но почему?

const name1 = JSON.stringify('fatfish') // => '"fatfish"'
const name2 = 'fatfish'

console.log(name1 === name2) // '"fatfish"' === 'fatfish' => false

Будьте осторожны при использовании JSON.stringify для сравнения со строками  —  можете оказаться в тупике.

Читайте также:

Читайте нас в TelegramVK и Дзен


Перевод статьи fatfish: Interviewer: Why Do “false == []” And “false == ![]” Both Return true?

Предыдущая статья11 инструментов для ускорения создания пользовательского интерфейса
Следующая статьяMermaid: универсальный инструмент для создания диаграмм