*hoisting: ๋์ด ์ฌ๋ฆฌ๊ธฐ
hoist์ ์ฌ์ ์ ์๋ฏธ๋ '๋์ด ์ฌ๋ฆฌ๊ธฐ' ๋ผ๋ ๋ป์ด๋ค. ๋ณ์๋ ํจ์์ ํธ์ถ ์ฝ๋๋ณด๋ค, ์ ์ธ ์ฝ๋๊ฐ ์๋ซ์ชฝ์ ์์์๋ ๋ถ๊ตฌํ๊ณ ์๋ฌ๊ฐ ๋ฐ์ํ์ง ์๊ณ , ๋ง์น ์ ์ธ ์ฝ๋๊ฐ ํธ์ถ ์ฝ๋๋ณด๋ค ๋ ์์ ์ ์ธ๋ ๊ฒ๊ณผ ๊ฐ์ด ๋์ํ๋ ํน์ฑ์ hoisting(ํธ์ด์คํ ) ์ด๋ผ๊ณ ํ๋ค.
์ฒ์๋ถํฐ ์ด ๋ง์ ์ดํดํ๋ ค๊ณ ํ๋ฉด ์ ์ ๋ ๊ฒ์ด๋ค. ์ฐ์ ์๋ฐ์คํฌ๋ฆฝํธ์์ ๋ณ์๋ฅผ ์ ์ธํ๋ ๋ฐฉ๋ฒ ์ค, let๊ณผ var์ ์ฐจ์ด์ ๋ถํฐ ์ง๊ณ ๋์ด๊ฐ์ผ ํธ์ด์คํ ์ ๊ฐ๋ ์ ๋ ์ ํํ๊ฒ ์ดํดํ ์ ์๋ค.
let๊ณผ var์ ์ฐจ์ด: ํ์ด์ var๋ ๋ฌธ์ ๊ฐ ๋ง์๋ค..
์๋ ์์ ์๋ ์ง๊ธ์ ์ฐ๋ฆฌ๊ฐ ๋๋ฆฌ ์ฐ๊ณ ์๋ let์ด ์๋, var๋ง ์ฌ์ฉํ๋ค๊ณ ํ๋ค. ๊ทธ๋ฌ๋ค ECMA-262 ๊ธฐ์ ๊ท๊ฒฉ์ ๋ฐ๋ผ ์ ์ํ๊ณ ์๋ ํ์คํ๋ ์คํฌ๋ฆฝํธ ํ๋ก๊ทธ๋๋ฐ ์ธ์ด์ธ ECMAScript๊ฐ 2015๋ 6์์ ES6๋ก ์ ๊ทธ๋ ์ด๋๋ฅผ ํ๋๋ฐ, ์ด๋ let์ด ์ฒ์ ๋์ค๊ธฐ ์์ํ ๊ฒ์ด๋ค. ์ฆ, var ์ฌ์ฉ ์ ๋ฌธ์ ๊ฐ ์์๊ธฐ ๋๋ฌธ์ ์ ๊ทธ๋ ์ด๋๋ฅผ ํ ๊ฒ์ด๋ค. var ์ฌ์ฉ์ ๋์ฒด ์ด๋ค ๋ฌธ์ ๊ฐ ์์๊ธธ๋?
1. ๊ฐ์ ์ ์ธ๋ ํ๊ธฐ ์ ์ ํ ๋นํ ์ ์์
์๋์ ๊ฐ์ด ์ฝ๋๋ฅผ ์ ๋ ฅํ๊ณ , ์ฝ๋๊ฐ ์คํ๋๊ธฐ ์ ์ ์๋ฐ์คํฌ๋ฆฝํธ๋ ๋จผ์ ์ ์ธ๋ ๋ณ์์ ํจ์๋ฅผ ๊ฐ์ ธ๊ฐ์ ๋ฉ๋ชจ๋ฆฌ์ ๊ธฐ์ต์ ํด๋๋ค. ์ฆ, ์๋ฐ์คํฌ๋ฆฝํธ ๋ผ๋ ์ ์๋์ด ์์ ์ ์์ํ๊ธฐ ์ ์(= ์ฝ๋๋ฅผ ์คํํ๊ธฐ ์ ์) ์ด๋ค ํ์๋ค์ด ์๋์ง(= ์ด๋ค ๋ณ์๋ค์ด ์๋์ง) ์กฐ์ฌ(= ์ถ์์ฒดํฌ) ๋ฅผ ํ๋ค๊ณ ๋ณด๋ฉด ๋๋ค. ๊ทธ๋ฌ๋ค, ๋๊ฐ ella ๋ผ๋ ๋ณ์๋ฅผ ๋ถ๋ฅด๋ฉด ๊ทธ ๋ณ์๊ฐ ๋์ค๋ ๊ฒ์ด๋ค. ์ฆ, ํจ์๊ฐ ์คํ๋๊ธฐ ์ ์ ์์ ์๋ ๋ณ์๋ค์ ๋ฒ์์ ์ต์๋จ์ผ๋ก ์ฌ๋ ค ๋ณด๋ด๋ ๊ฒ์ด๋ค.
var age = 10
var name = "Ella"
var student = true
console.log(age)
์ฝ๋๋ฅผ ํตํด ํ๋ฒ ๋ ์ค๋ช ํด ๋ณด๊ฒ ๋ค. ์ฒซ ๋ฒ์งธ ์ฝ๋๋ ๋ฌธ์ ์์ด 1์ด ์ ์ถ๋ ฅ๋ ๊ฒ์ด๋ค.
var ella = 1 // var๋ก ๋ณ์ ella๋ฅผ ์ ์ธํ๊ณ , ๋ณ์์ ๊ฐ์ 1๋ก ํ ๋น
console.log(ella) // 1
ํ์ง๋ง ๋ ๋ฒ์งธ ์ฝ๋๋ ella๊ฐ ์ ์ธ๋๊ธฐ๋ ์ ์ ella๋ฅผ ์จ์ ์๋ฌ๊ฐ ๋ ๊ฒ ๊ฐ๋ค. ์ฝ๋๋ ์๋์์ ์๋ก ํ๋ฌ๊ฐ๊ธฐ ๋๋ฌธ์ด๋ค. ํ์ง๋ง ์ฐ๋ฆฌ์ ์๋ฐ์คํฌ๋ฆฝํธ ์ ์๋์ ์๋ฌ๋ฅผ ๋ด์ง ์๊ณ undefined์ 1์ ์ถ๋ ฅํ๋ค.
console.log(ella) // undefined
var ella = 1
console.log(ella) // 1
์? ๋ฐ๋ก ํธ์ด์คํ ๋๋ฌธ์ด๋ค. ์ฐ๋ฆฌ ์๋ํ์ ์๋ฐ์คํฌ๋ฆฝํธ ์ ์๋์ ์ฝ๋ ์ฒซ ๋ฒ์งธ ์ค์์๋ถํฐ ella๊ฐ ์์ผ๋ฉด ๋ฐ๋ก ์๋ฌ๋ฅผ ๋ด๋๊ฒ ์๋๋ผ, undefined๋ฅผ ์ฃผ๋ฉด์ ์์ง ํ ๋น๋์ง ์์์์ ์ด์ผ๊ธฐํ๊ณ , ๋ค์ด์ด ๋ ๋ฒ์งธ ์ค์ ella๊ฐ ์์์ ๋ฐ๊ฒฌํ ํ 1์ ์ถ๋ ฅํ๋ค. ์ฆ, ์ถ์์ ํ์ง ์์๋ค๊ณ ๋ฐ๋ก ๊ฒฐ์์ฒ๋ฆฌ๋ฅผ ํ๊ฒ ์๋๋ผ ์ถ์ ๋ณด๋ฅ ์ฒ๋ฆฌ๋ฅผ ํ ๊ฒ์ด๋ผ๊ณ ๋ณด๋ฉด ๋๋ค.
์ด๋ป๊ฒ ์ด๋ฐ ๊ฒ์ด ๊ฐ๋ฅํ ๊น? ํธ์ด์คํ ์ ํ๋ฉด ๋ณ์์ ์ ์ธ๊ณผ (undefinded ๋ก) ์ด๊ธฐํ๋ฅผ ๊ฐ์ด ์์ผ๋ฒ๋ฆฌ๊ณ , ๊ฐ ํ ๋น์ ๋์ค์ ella๊ฐ ์๋ ํด๋น ์ค์ ๊ฐ์ ํ๋ค.
์ฌ์ง์ด ์ ์ธ๋ ํ์ง ์๊ณ , ์ ์ธ์ ํ ๋น ๋ค์ ํด๋ฒ๋ ค๋ undefined์ 1์ด ๋์จ๋ค.
console.log(ella) // undefined
ella = 1
var ella
console.log(ella) // 1
2. ์ ์ญ๋ณ์์ ์ง์ญ๋ณ์์ ๊ฐ๋ ์ด ํ์คํ์ง ์์
์ฌ๊ธฐ์ ์ ๊น, ์ ์ญ๋ณ์์ ์ง์ญ๋ณ์์ ์ฐจ์ด๋ฅผ ๋ชจ๋ฅธ๋ค๋ฉด ๋จผ์ ์๊ณ ๊ฐ์.
์ ์ญ๋ณ์๋ ์ด๋ ํ ๋ฒ์๋ ์์ด ๋ธ๋ฝ { } ๋ฐ์์ ์ ์ธ์ ํ ์ด๋์๋ ์ฐ์ผ ์ ์๋ ๋ณ์๋ค.
var ella = 2
์ง์ญ๋ณ์๋ function์ด๋ for๋ฌธ ๋ฑ์ ๋ธ๋ฝ { } ์์์ ์ ์ธ๋ ๋ณ์์ด๋ฉฐ ๋ธ๋ฝ ์์์๋ง ์ธ ์ ์๋ค.
var ella = "yes"; // ์ ์ญ ๋ณ์ ella
function attend() {
var chloe = "..."; // ์ง์ญ ๋ณ์ chloe
}
console.log(chloe);
// ReferenceError: chloe is not defined
// { } ์ง์ญ์ ๋ฒ์ด๋๋ฉด ์๋ฌ๊ฐ ๋จ
๋ ๋ณ์์ ์ฐจ์ด๋ฅผ ์ ์ดํดํ๋ค๋ฉด ์๋์ for๋ฌธ ์์ ์ฝ๋๋ฅผ ๋ค์ ๋ณด์.
for(var i = 1; i < 5; i++) {
console.log(i)
}
console.log(i) // 1 2 3 4 5: ์๋ฌ๊ฐ ๋์ง ์์
์ฌ๊ธฐ์ var i ๋ for๋ฌธ { } ์์์ ์ ์ธ์ด ๋๊ธฐ ๋๋ฌธ์ ๋ธ๋ฝ ๋ฐ์์ i๋ฅผ ์ถ๋ ฅํ๋ ค๊ณ ํ๋ฉด ์๋ฌ๊ฐ ๋์ผ ํ๋ ๊ฒ์ด ๋ง๋ค. ํ์ง๋ง ์๋ฌ๊ฐ ๋์ง ์๋๋ค. ์ฆ, var๋ฅผ ์ฌ์ฉํ๋ฉด ํจ์(function)๋ง ์ง์ญ๋ณ์๋ก ํธ์ด์คํ ์ด ๋๊ณ , ๋๋จธ์ง(for๋ฌธ, if๋ฌธ ๋ฑ)๋ ๋ค ์ ์ญ๋ณ์๋ก ์ฌ๋ ค๋ฒ๋ฆฌ๋ ๊ฒ์ด๋ค.
3. ๊ฐ์ ์ด๋ฆ์ ๋ณ์๊ฐ ๋ ๊ฐ ์ด์์ด ๋ ์ ์์
var ella = 1
console.log(ella) // 1
var ella = 2
console.log(ella) // 2
๋ณ์์ ์ด๋ฆ์ ์ ๋๋ก ์ค๋ณต์ด ๋์ง ๋ง์์ผ ํ๋๋ฐ, ์์ ๊ฐ์ ์ํฉ์ด๋ผ๋ฉด ๋์ ๊ฐ์ ์ฃผ๋ฏผ๋ฑ๋ก๋ฒํธ๊ฐ ๊ฐ์ ์ฌ๋์ด ๋ ๋ช ์ด ์๋ค๋ ๋ป์ด๋ค. ์์ ๊ฐ์ด ์ฝ๋๋ฅผ ์ง๋ฉด ํนํ ํฐ ํ๋ก์ ํธ์ผ์๋ก ๊ต์ฅํ ํผ๋์ด ์ฌ ๊ฒ์ด๋ค.
์ ์ธ ๊ฐ์ง ์ด์ ๋ก ์ธํด var์ ๋ฌธ์ ์ ๋ค์ ๋ณด์ํ let์ ๋ง๋ค์๋ค.
์์ ์ฝ๋์์ var์ let์ผ๋ก ๋ฐ๊ฟ๋ณด๋ฉด ์ ์์ ์ผ๋ก(?) ์๋ฌ๊ฐ ์ ๋๋ค. ella ๋ผ๋ ๋ณ์๊ฐ ์ด๋ฏธ ์ ์ธ์ด ๋์์ผ๋, ์ค๋ณต์ผ๋ก ์ ์ธํ ์ ์๋ค๋ ๋ป์ด๋ค.
let ella = 1
console.log(ella)
let ella = 2
console.log(ella) // SyntaxError: Identifier 'ella' has already been declared
๋ง์ฐฌ๊ฐ์ง๋ก ์์ ์์ฑํ๋ for๋ฌธ ์์๋ let์ผ๋ก ๋ณ๊ฒฝํ๋ฉด i๊ฐ ์ ์๋์ง ์์๋ค๋ ์ ์์ ์ธ ์๋ฌ๊ฐ ๋๋ค. i๋ ์ง์ญ๋ณ์๋ก ์ ์ธ์ด ๋์๋๋ฐ, ๋ธ๋ก ๋ฐ์ ์๋ console.log(i)๋ ๋ธ๋ก ์์ ์๋ ์ง์ญ๋ณ์์ ์ ๊ทผํ ์ ์๋ค๋ ๋ป์ด๋ค.
for(let i = 1; i < 5; i++) {
console.log(i)
}
console.log(i) // ReferenceError: i is not defined
๋ง์ง๋ง์ผ๋ก, ์ฒ์์ ์์ฑํ๋ ์ฝ๋ ์์์๋ var ๋์ let์ ์ฌ์ฉํ๋ฉด ์ ์์ ์ธ ์๋ฌ๊ฐ ๋๋ค. ์ด๊ธฐํ๊ฐ ๋๊ธฐ ์ ์ ella ์ ์ ๊ทผํ ์ ์๋ค๋ ์๋ฏธ๋ค.
console.log(ella)
let ella = 1
console.log(ella) // ReferenceError: Cannot access 'ella' before initialization
let์ ์ฌ์ฉํ๋ ์๊ฐ, ๋ชจ๋ ๋ฌธ์ ๊ฐ ํด๊ฒฐ์ด ๋์๋ค!
let์ ์ด ๋ฌธ์ ๋ฅผ ์ด๋ป๊ฒ ํด๊ฒฐํ ๊ฒ์ผ๊น? ์ฌ์ค, let๋ ํธ์ด์คํ ์ด ๋๋ค.
console.log(ella) // TDZ: ์์ง ella๊ฐ ์ ์ธ๋์ง ์์์ผ๋ฏ๋ก ์ผ์์ ์ผ๋ก ์ฃฝ์ zone์
let ella = 1 // ๋ค๋ฆ๊ฒ ella ์ ์ธํจ
console.log(ella) // ReferenceError: Cannot access 'ella' before initialization: ๊ทธ๋๋ ์๋ฌ๋จ
ํ์ง๋ง let์ด๋ผ๋ ๊ฐ๋ ์ ๋ง๋ค๋ฉด์ TDZ(Temporal Death Zone)์ด๋ผ๋ ๊ฐ๋ ๋ ํจ๊ป ๋ง๋ค์๋๋ฐ, ์ด๋ฏธ ์ฝ๋ ์ฒซ ๋ฒ์งธ ์ค์์ ella๊ฐ ํธ์ด์คํ ์ด ๋ ๊ฒ์ ์์ง๋ง, ella ์ ์ธ๋ฌธ์ด ๋์ค๊ธฐ ์ ๊น์ง๋ ella์ ์ ๊ทผํ ์ ์๋ค๋ ์๋ฏธ == ์ฆ ์ผ์์ ์ผ๋ก ์ฃฝ์ zone ์ด๋ค. ella๊ฐ ์ด๊ธฐํ(initialization)๊ฐ ๋ ๋๊น์ง๋ ์๋ฌด๋ฆฌ ella์ ์ ๊ทผํด๋ ์ค์ ๋ก ์ ์ธ๋๊ณ ํ ๋น๋๋ ๋ผ์ธ ์ ๊น์ง๋ ella๋ฅผ ์ธ ์ ์๋ค. ๋ฐ๋ผ์ ์๋์ ๊ฐ์ด ์ฝ๋๋ฅผ ์์ฑํด์ผ ํ๋ค.
let ella = 1 // ella ์ ์ธํจ
console.log(ella) // 1์ด ์ถ๋ ฅ๋จ
๊ทธ๋์ let๊ณผ const์์๋ ์ด๋ป๊ฒ ํธ์ด์คํ ๋๋๋ฐ?
function a () {
for(let i = 0; i < 10; i++){
}
return i;
}
console.log(a()) // ReferenceError: i is not defined: ๋ธ๋ก ๋ฐ์์ return ํ๊ธฐ ๋๋ฌธ
์ฐ์ , var๋ function scope (= ํจ์ ๋ด์์ ๋ณ์๊ฐ ์ ๊ทผํ ์ ์๋ ์์ญ), let๊ณผ const๋ block scope (= ๋ธ๋ก ๋ด์์ ๋ณ์๊ฐ ์ ๊ทผํ ์ ์๋ ์์ญ)์ด๋ค. ๋ฐ๋ผ์ ์์ ์ฝ๋์์ i๋ for๋ฌธ ๋ธ๋ก ์์์๋ง ์ ๊ทผ์ด ๊ฐ๋ฅํ๊ธฐ ๋๋ฌธ์ return์ ํ๋ฉด ์ฐธ์กฐ๊ฐ ๋ถ๊ฐ๋ฅํ๋ค๋ ์๋ฌ๊ฐ ๋๋ค.
let a = 1
if(true) {
console.log(a) // Cannot access 'a' before initialization: ํธ์ด์คํ
๋์ด ์ฐธ์กฐ๋ฅผ ํ ์ ์๊ฒ ๋จ
let a = 2
}
๋ค์ ํ๋ฒ ๋งํ์ง๋ง, ํธ์ด์คํ ์ ๋ธ๋ก ์ค์ฝํ๋ ํจ์ ์ค์ฝํ ๋ด์ ์ต์๋จ์ผ๋ก ๊ฐ๋ ๊ฒ์ ๋งํ๋๋ฐ, console.log(a)๋ก a๋ฅผ ์ถ๋ ฅํ ๋๋ ํธ์ด์คํ ๋์ด ์ฐธ์กฐ๋ฅผ ํ ์ ์๊ฒ ๋๋ค. ํ์ง๋ง ์ด๋๋ ์ ์ธ๋ง ๋๊ณ ์ด๊ธฐํ๊ฐ ๋์ง ์์์ ์๋ฌ๊ฐ ๋๋ค. ์ ์ธํ ๋ณ์๊ฐ ํธ์ด์คํ ์ด ์ผ์ด๋๊ธด ํ์ง๋ง, let๊ณผ cost๋ ์ ์ธ๊ณผ ์ด๊ธฐํ๊ฐ ๋์์ ์ผ์ด๋์ง ์์๊ธฐ ๋๋ฌธ์ ์๋ฌ๊ฐ ๋ฐ์ํ ๊ฒ์ด๋ค. ์ฆ, ํธ์ด์คํ ์ด ์ผ์ด๋๊ธด ๋๋ค๋ ๊ฑฐ๋ค.
* var: ์ ์ธ ๋ฐ ์ด๊ธฐํ → ํ ๋น
* let, const: ์ ์ธ → TDZ → ์ด๊ธฐํ → ํ ๋น
์ ์๋ฌ๊ฐ ๋ฐ๊น? ๋ณดํต ์๋ฐ์คํฌ๋ฆฝํธ ์์ง์ undefined๋ก ์ด๊ธฐํ๊ฐ ๋๋๋ฐ, ์์ ๊ฐ์ด var๋ ์ ์ธ๊ณผ ๋์์ ์ผ์ด๋๋, let๊ณผ const๋ ์ ์ธ๊ณผ TDZ๊ฐ ์ค๊ฐ์ ๋ง๊ณ ์์ด์ ์ ์ธ๊ณผ ์ด๊ธฐํ๊ฐ ๋์์ ์ผ์ด๋์ง ์๊ธฐ์ ์ ์ธ์ ๋์์ผ๋ ์ด๊ธฐํ๊ฐ ๋์ง ์์๋ค๋ ์๋ฌ๊ฐ ๋๋ค.
๋ฐ๋ผ์, ์๋์ ๊ฐ์ด ์์ฑํ๋ฉด ๋์ถํ๊ณ ์ ํ๋ ๊ฐ์ด ์ ์์ ์ผ๋ก ๋์จ๋ค.
let a = 1
if(true) {
let a = 2
console.log(a) // 2
}
๊ฒฐ๋ก : var ์ฐ์ง ๋ง๊ณ , let ์ฐ์!
๋ด์ฉ ์ฐธ์กฐ
- Youtube : ํฐ๋์ํฐ์ <์๋ฐ์คํฌ๋ฆฝํธ const์ let์ ํธ์ด์คํ >
๋๊ธ