Hoisting
В одной фразе: hoisting — поведение фазы “создания” execution context, в которой объявления переменных и функций регистрируются до выполнения кода. var инициализируется как undefined, function declaration поднимается полностью; let/const/class — в TDZ.
// var: поднимается объявление, не инициализация → undefinedconsole.log(x); // undefined — не ReferenceError!var x = 5;console.log(x); // 5
// Как это видит движок концептуально:// var x; ← создание контекста: x = undefined// console.log(x); ← undefined// x = 5;// console.log(x); ← 5// function declaration: поднимается ПОЛНОСТЬЮ — имя + телоgreet('World'); // 'Hello, World' — вызов до объявления работает!function greet(name) { console.log(`Hello, ${name}`);}
// function expression: поднимается только переменная (var → undefined)sayHi('Bob'); // TypeError: sayHi is not a functionvar sayHi = function(name) { console.log(`Hi, ${name}`); };
// let/const: TDZ — ReferenceError при доступе до инициализации// Приоритет: function declaration перебивает var при одинаковом имениconsole.log(typeof foo); // 'function' — declaration поднялась первойvar foo = 1;function foo() {} // hoisted выше varconsole.log(typeof foo); // 'number' — присваивание var foo=1 выполнилось
// class declaration: hoisted, но в TDZ// new Animal(); // ReferenceError: Cannot access 'Animal' before initializationclass Animal { constructor(name) { this.name = name; } }new Animal('Cat'); // OK — после объявленияИтог: Hoisting — не перемещение кода, а особенность фазы создания execution context. var → undefined, function declaration → полная функция, let/const/class → TDZ.