Какие вопросы об отладке часто задают на собеседовании JS-разработчикам: примеры и объяснения
2026-02-26 17:09 Diff

В подборку попали типичные вопросы об отладке, с которыми сталкиваются на собеседованиях разработчики на JavaScript. Попытайтесь ответить на них самостоятельно, а потом сравните ответ с правильным решением.

Содержание

Вопрос 1: объекты и ссылки на объекты

Почему вместо hey amy получаем результат hey arnold?

Ответ

Вот секрет: { name: 'amy' } !== { name: 'amy' }. Когда JavaScript проверяет равенство или строгое равенство объектов, он использует ссылки на объект. В данном случае мы видим объекты с одинаковыми свойствами. Но для JavaScript это два разных объекта.

Чтобы получить ожидаемый результат, нужно использовать такой код:

Вопрос 2: область видимости и event loop

Почему код из примера ниже не выводит значения с 0 до 3 по порядку?

Проблема

Это неочевидный вопрос. Чтобы правильно ответить на него, нужно понимать область видимости и цикл событий (event loop) в JavaScript.

Проблема прячется в нулевой задержке. setTimeout(() => console.log(i), 0) не значит, что колбэк выполнится через 0 миллисекунд. Посмотрим на код через призму event loop:

  1. Текущий стек вызовов установлен для первого setTimeout().
  2. window.setTimeout() рассматривается в качестве веб API для выполнения неблокирующих операций ввода-вывода (I/O). Стек вызовов отправляет этот код в веб API. Через 0 миллисекунд колбэк, в данном случае — анонимная функция, отправляется в очередь (queue), но не в стек вызовов.
  3. Поскольку стек вызовов свободен, цикл for переходит ко второму setTimeout() и работает, пока верно условие i < 4.
  4. Цикл завершается, когда i === 4. Теперь JavaScript выполняет очередь колбэков. Каждый console.log(i) выводит 4.

Ещё одна проблема связана с областью видимости. В примере выше четыре экземпляра setTimeout() работают с одним экземпляром i. Это хорошо иллюстрирует код из примера ниже.

Ответ

Задачу можно решить несколькими способами. Первый — используйте функцию-обёртку для setTimeout().

Второй способ — просто используйте ключевое слово let вместо var. Переменная, объявленная с помощью var, сохраняется при каждом повторении цикла. А при использовании let при каждом повторении цикла создаётся новая переменная.

Вопрос 3: контекст функции

Дан код:

Почему получаем результат undefined?

Ответ

В коде выше определяется объект dog, в котором два свойства. Мы копируем свойство объекта в константу sayName, а затем вызываем sayName в глобальном контексте. Функция sayName() возвращает window.name, так как в Node.js вызов происходит в глобальном контексте, где typeof window.name === 'undefined'.

Проблему можно решить двумя способами: удобным и не очень. Сначала не очень удобный подход: привязываем sayName к контексту dog с помощью bind.

Более удобный подход: сразу вызываем функцию в нужном контексте.

Вопрос 4: прототипы и ключевое слово class

Дан код:

Почему собака по кличке fido не лает?

Ответ

В выводе появляется ошибка: TypeError: fido.bark is not a function. Есть несколько решений задачи. Вот не самый удобный подход:

fido.bark — не функция, но у нас есть функция Dog.bark. Поэтому в примере выше решаем задачу с помощью function.prototype.bind(). Но использование function.prototype.bind() часто приводит к проблемам, поэтому удобнее определить bark() в прототипе Dog:

И самый удобный вариант: использовать синтаксис ES2015, в частности, ключевое слово class.

Вопрос 5: строгое равенство

Почему код из примера ниже ведёт себя не так, как мы ожидаем?

Ответ

В коде используется оператор сравнения ==. Этот оператор позволяет сравнивать разные типы данных. Вот что происходит.

С аргументом 1 функция isBig() работает как ожидается. При вызове isBig([2]) срабатывает условие thing == 2. При сравнении массива и числа JavaScript преобразует массив в число. Так работает алгоритм сравнения абстрактного равенства: когда мы сравниваем число и объект, а массивы в JS — это объекты, объект преобразуется в число. В нашем массиве один элемент, поэтому [2] == 2.

Неявные преобразования сложно отслеживать, поэтому при использовании оператора == возможны сюрпризы. Рекомендуется использовать оператор сравнения ===.

Вместо заключения

У нас есть репозиторий с реальными тестовыми заданиями от разных компаний. Используйте его, чтобы оценить свой уровень и прокачаться перед собеседованиями. А если у вас остались вопросы по задачам для JavaScript-разработчиков, пишите в комментариях.

Адаптированный перевод статьи Typical JavaScript interview exercises (explained) by Maxence Poutord.