setTimeout()을 사용할 때, this가 기대한 객체를 가리키지 않는 문제는 JavaScript의 this 바인딩 특성 때문에 발생합니다.
setTimeout()은 콜백 함수 내부에서 실행되므로, 해당 함수의 this는 기본적으로 전역 객체 (window 또는 undefined in strict mode) 를 가리킵니다.
즉, this가 원래 객체를 가리키지 않고 사라진 것처럼 보이는 것입니다.
const obj = {
name: "Alice",
sayHi: function () {
console.log(this.name); // Alice
setTimeout(function () {
console.log(this.name); // ❌ undefined (브라우저에서는 window.name)
}, 1000);
},
};
obj.sayHi();
bind(this)를 사용하여 this가 원하는 객체를 가리키도록 고정할 수 있습니다.
const obj = {
name: "Alice",
sayHi: function () {
console.log(this.name); // Alice
setTimeout(
function () {
console.log(this.name); // ✅ Alice
}.bind(this),
1000
);
},
};
obj.sayHi();
✔ bind(this)를 사용하면 this가 항상 obj를 가리키도록 고정됩니다.
화살표 함수는 자신만의 this를 생성하지 않으며, 상위 스코프의 this를 유지합니다.
const obj = {
name: "Alice",
sayHi: function () {
console.log(this.name); // Alice
setTimeout(() => {
console.log(this.name); // ✅ Alice
}, 1000);
},
};
obj.sayHi();
✔ 화살표 함수 내부에서는 this가 상위 함수의 this(= obj) 를 유지하기 때문에 문제없이 동작합니다.
이전 방식이긴 하지만, this를 변수에 저장하는 방법도 있습니다.
const obj = {
name: "Alice",
sayHi: function () {
var self = this; // ✅ this를 변수에 저장
setTimeout(function () {
console.log(self.name); // ✅ Alice
}, 1000);
},
};
obj.sayHi();
✔ 콜백 함수 내부에서 this를 잃어버리지 않도록, this를 self라는 변수에 할당하는 방식입니다.
✔ 요즘은 bind()나 화살표 함수를 더 많이 사용합니다.
해결 방법 | 코드 예시 | 설명 |
---|---|---|
bind(this) | setTimeout(function(){}.bind(this), 1000); | this를 수동으로 고정 |
화살표 함수 | setTimeout(() => {}, 1000); | 상위 스코프의 this 유지 |
self 변수 | var self = this; setTimeout(function(){}, 1000); | this를 다른 변수에 저장 |
✅ ES6 이후 → 화살표 함수 (=>) 사용
✅ ES5 환경 → bind(this) 사용