Типичные задачи JS-собеса и подходы

Каталог задач из живых JS-собесов AsForJS и автора с подходом к ответу. Не зубрёжка ответов, а структура мышления.

Суть

Собесы любят набор стандартных задач: this, типы, замыкания, event loop, Promise. У каждой задачи есть «социально одобряемый» ответ и реальный, основанный на спецификации. Важно понимать оба уровня.

Задача: потеря this

const obj = { say { console.log(this); } };
const fn = obj.say;
fn;          // потеря this
fn.call(obj);  // вернуть
  • В non-strict this будет global, в strict — undefined
  • Возврат через call/apply/bind
  • На уровне спеки: this — особый идентификатор, устанавливается формой вызова
  • Метод не «принадлежит» объекту — obj.say это просто ссылка на функцию

Задача: numberWithSpaces

Разбить число на тройки с пробелами: 12345671 234 567

  • Не регулярка с lookahead (медленно)
  • Самописный цикл с накоплением
  • Тестировать на разной длине
  • Понять, нужны ли отрицательные/дробные

Задача: this так, this сяк

const obj = {
  foo { return this; },
  bar:  => this,
  baz: function { return this; }
};
  • Стрелочная функция не имеет своего this — берёт лексический
  • Ordinary function — устанавливается по форме вызова
  • Метод объекта — this на объекте, если вызван через obj.method

Задача: палиндром / плоский массив / поиск пути

  • Не выпендриваться, не писать «гениальный однострочник»
  • Простой алгоритм с понятным именованием
  • Проверить edge cases: пустой массив, рекурсия, циклы
  • Объяснить сложность вслух (O(n), O(n*m))

Задача: wtfjs.com

  • + === "", {} + === 0, 0.1 + 0.2 !== 0.3
  • Это про приведение типов и спецификацию
  • Не нужно знать каждый сюрприз
  • Нужно знать, как разобрать любой такой пример пошагово

Задача: типы и приведение

  • typeof null === 'object' (легаси спеки)
  • В JS coercion есть — несмотря на споры
  • ToPrimitive: hint string/number/default
  • Symbol.toPrimitive — кастомное приведение
  • NaN — диапазон из 9 квадриллионов чисел (внутри IEEE-754)

Задача: микротаски и макротаски

setTimeout( => console.log('macro'), 0);
Promise.resolve.then( => console.log('micro'));
// порядок: micro, macro
  • Микротаски выполняются после текущего synchronous кода
  • Перед следующим macrotask
  • queueMicrotask добавляет в очередь микротасок
  • Знать наизусть — необязательно, важно уметь проверить

Задача: try-catch и Promise

try {
  Promise.reject('err'); // не поймается!
} catch (e) {
  // не сработает
}

// правильно:
Promise.reject('err').catch(e => /* */);
  • try-catch ловит только синхронные ошибки
  • Async-функции с await — ловятся в try-catch
  • Без await Promise живёт сам по себе

Подход к любой задаче на собесе

  1. Понять задачу — переспросить условия
  2. Привести пример входа/выхода
  3. Edge cases — пустой, null, отрицательный
  4. Простое решение «в лоб», потом оптимизация
  5. Объяснить сложность вслух
  6. Тестировать вручную на 2-3 примерах
  7. Если не знаешь — честно сказать, что нагуглил бы и проверил

Антипаттерны

  • Молча писать код
  • Игнорировать edge cases
  • «Гениальные» однострочники без объяснения
  • Пытаться выдать ответ из памяти, когда не уверен
  • Стесняться попросить уточнения

🎓 Источники

  • 🎓 [автор на собеседовании] · AsForJS · 2025-03-02 · YouTube
    • Тезисы: this не контекст; reference type; микротаски/макротаски; try-catch и Promise
  • 🎓 [Вирішуємо завдання із співбесід this так, this сяк] · AsForJS · 2024-04-19 · YouTube
  • 🎓 [Решение задачи с собеседования numberWithSpaces] · AsForJS · 2024-04-16 · YouTube
  • 🎓 [JavaScript задачи собеседований Палиндром, плоский массив] · AsForJS · 2023-09-18 · YouTube
  • 🎓 [JavaScript собеседования: задачи wtfjs.com] · AsForJS · 2023-09-28 · YouTube
  • 🎓 [💡 JavaScript собеседование вопросы по асинхронному] · 2024-06-29 · YouTube