JS Basics
Что такое замыкание (Closure)?
Замыкание — это функция, которая запоминает переменные из внешней области видимости, даже после того как та область завершила выполнение.
function counter() {
let count = 0;
return () => ++count;
}
const inc = counter();
inc(); // 1
inc(); // 2
// count недоступен снаружи, но функция его помнитПрактические применения:
- Инкапсуляция приватного состояния.
- Фабричные функции с параметрами.
- Мемоизация и каррирование.
Прототипы и прототипное наследование
Каждый объект в JS имеет скрытую ссылку [[Prototype]] на другой объект. При обращении к свойству JS ищет его сначала в самом объекте, затем поднимается по цепочке прототипов.
const animal = { eat() { return 'eating'; } };
const dog = Object.create(animal);
dog.bark = () => 'woof';
dog.bark(); // 'woof' — собственный метод
dog.eat(); // 'eating' — унаследован от animal
dog.__proto__ === animal; // true// class — синтаксический сахар над прототипами
class Animal {
eat() { return 'eating'; }
}
class Dog extends Animal {
bark() { return 'woof'; }
}
const d = new Dog();
d.eat(); // 'eating' — через цепочку прототипов
Object.getPrototypeOf(obj)— правильный способ получить прототип вместо__proto__.
Функции и массивы — это объекты?
Да. Функции и массивы — специализированные объекты, наследующие от Object.prototype.
// Функция — объект
const fn = () => {};
fn.myProp = 'hello';
fn.myProp; // 'hello'
fn instanceof Object; // true
typeof fn; // 'function' — это лишь подтип, не отдельный тип
// Массив — объект
const arr = [1, 2, 3];
arr instanceof Object; // true
typeof arr; // 'object'
Array.isArray(arr); // true| Значение | typeof | На самом деле |
|---|---|---|
function(){} | 'function' | Объект (подтип Function) |
[] | 'object' | Объект (подтип Array) |
null | 'object' | Не объект (баг JS) |
Как проверить, что переменная содержит функцию?
const fn = () => {};
// ✅ Лучший способ — typeof
typeof fn === 'function'; // true
typeof null === 'function'; // false — не обманет
// instanceof — ненадёжен в разных контекстах (iframe)
fn instanceof Function; // true
// Максимально точно — Object.prototype.toString
Object.prototype.toString.call(fn); // '[object Function]'На практике всегда используют
typeof— он лаконичен и корректно обрабатываетnull.
Как проверить, что значение — массив?
const arr = [1, 2, 3];
// ✅ Лучший способ — Array.isArray
Array.isArray(arr); // true
Array.isArray({}); // false
Array.isArray(null); // false
// Устаревшие / ненадёжные способы
arr instanceof Array; // true — ломается в iframe
typeof arr; // 'object' — не отличает от {}
Array.isArray— единственный надёжный способ в любом контексте.