화살표 함수를 객체 메서드로 사용하면 안 되는 이유
JavaScript의 화살표 함수(arrow function)는 일반 함수와 달리 자신만의 this를 갖지 않습니다. 대신 화살표 함수가 선언된 위치를 둘러싼 렉시컬 스코프(lexical scope)의 this 값을 그대로 물려받습니다. 전역 범위에서 이 값은 곧 window 객체입니다.
따라서 객체 리터럴 내부에서 화살표 함수로 메서드를 정의하면, 그 메서드 안의 this는 객체 자신이 아니라 window 객체를 가리키게 됩니다. 그 결과 개발자는 의도했던 객체의 속성이 아니라 window 객체의 속성을 읽고 쓰게 되어 예상치 못한 버그가 발생합니다.
문제가 되는 코드 예제
다음은 화살표 함수를 사용하면 안 되는 경우를 보여주는 예제 코드입니다.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Document</title>
<style>
body {
font-family: "Segoe UI", Tahoma, Geneva, Verdana, sans-serif;
}
.result {
font-size: 20px;
font-weight: 500;
color: blueviolet;
}
</style>
</head>
<body>
<h1>When to not use the arrow functions</h1>
<br />
<div class="result"></div>
<br />
<button class="Btn">CLICK HERE</button>
<h3>Click on the above button to call the add() method of object obj</h3>
<script>
let BtnEle = document.querySelector(".Btn");
let resEle = document.querySelector(".result");
let obj = {
a: 22,
b: 44,
add: () => {
return this.a + this.b;
},
};
BtnEle.addEventListener("click", (event) => {
resEle.innerHTML = `The sum of ${obj.a} and ${obj.b} = ${obj.add()}`;
});
</script>
</body>
</html>
실행 결과

'CLICK HERE' 버튼을 클릭하면 다음과 같이 출력됩니다. this.a와 this.b가 객체 obj가 아닌 window 객체를 참조하기 때문에 합계가 NaN으로 나오는 것을 확인할 수 있습니다.

올바른 해결 방법
객체의 메서드를 정의할 때는 일반 함수 표현식이나 ES6의 메서드 축약형(method shorthand)을 사용해야 합니다.
let obj = {
a: 22,
b: 44,
add() {
return this.a + this.b;
},
};
이렇게 작성하면 this가 메서드를 호출한 객체(obj)에 바인딩되므로, 버튼을 클릭했을 때 22 + 44 = 66이라는 올바른 결과를 얻을 수 있습니다.
화살표 함수를 피해야 하는 다른 경우
- DOM 이벤트 핸들러: 이벤트가 발생한 요소에 접근하려면
this가 해당 요소를 가리켜야 하는데, 화살표 함수를 사용하면this가 외부 스코프를 참조하게 됩니다. - 생성자 함수: 화살표 함수에는 내부 슬롯 [[Construct]]가 없어
new키워드와 함께 호출할 수 없습니다. - prototype 메서드: 프로토타입에 정의된 메서드도 호출 주체 객체에
this가 바인딩되어야 하므로 일반 함수를 사용해야 합니다. - arguments 객체가 필요한 경우: 화살표 함수는 자체
arguments객체를 갖지 않으므로, 가변 인자를 처리하려면 일반 함수나 나머지 매개변수(rest parameter)를 활용해야 합니다.
정리하면, 화살표 함수는 콜백이나 짧은 유틸리티 함수처럼 this 바인딩이 필요 없는 상황에서 빛을 발합니다. 반면 객체 메서드, 이벤트 핸들러, 생성자처럼 this가 호출 주체를 가리켜야 하는 경우에는 반드시 일반 함수를 사용하는 것이 안전합니다.