아래와 같은 생성자 함수가 있다.
function Circle(radius) {
...
}
이 생성자 함수를 가지고 new Circle(5) 로 새로운 인스턴스를 생성했을때,
인수로 받은 radius 값 5를 생성한 인스턴스의 radius 값으로 할당하려면 어떻게 해야할까?
또, 아래와 같이 Circle의 prototype으로 지름을 구하는 메서드를 추가해서,
Circle 생성자 함수가 생성한 인스턴스의 지름을 구하려면 어떻게 해야할까?
Circle.prototype.getDiameter = function () {
...
}
닭이 먼저이냐 달걀이 먼저이냐의 문제처럼, 생성자 함수 내에서 생성자 함수가 생성할 인스턴스를 참조할 수는 없다.
왜냐하면, 생성자 함수가 먼저 정의되고 난 이후에야 생성자 함수를 가지고 인스턴스를 생성할 수 있기 때문이다.
이러한 상황을 해결하기 위해 자바스크립트는 this 라는 식별자를 제공한다.
this는 자기 참조 변수(self-reference variable)로, 자신이 생성할 인스턴스 또는 자신이 속한 객체를 가리킨다.
자바스크립트에서 함수를 호출하면 함수 내부에 암묵적으로 arguments 객체가 전달되는 것처럼, this 또한 자바스크립트 엔진에 의해 암묵적으로 생성되어 함수 호출 시 함수 내부에 arguments 객체와 함께 전달된다. 이때 this가 가리키는 값은 함수 호출 방식에 의해 동적으로 결정된다. (참고: 클래스 기반 언어(e.g. Java, C++) 의 경우 this는 항상 클래스가 생성할 인스턴스를 가리킨다)
this가 어떤 객체를 가리키게 될지 결정하는 것을 'this 바인딩 - this 식별자와 값(객체)을 연결(binding)' - 이라고 한다.
그러면 이제 위의 문제들로 돌아가보자.
새로운 인스턴스를 생성했을때, 인수로 받은 radius 값을 생성한 인스턴스의 radius 값으로 할당하려면 this 키워드를 사용한다.
function Circle(radius) {
this.radius = radius ;
}
마찬가지로, Circle 생성자 함수가 생성한 인스턴스의 지름을 구하는 메서드는 아래와 같이 this 키워드를 사용한다.
Circle.prototype.getDiameter = function () {
return this.radius * 2 ;
}
이제 Circle 생성자 함수로 새 인스턴스를 생성했을때, 인자로 받은 radius 값을 인스턴스의 할당할 수 있게 되었고, getDiameter 메서드를 호출하여 생성한 인스턴스의 지름을 구할 수 있게 되었다!
const smallCircle = new Circle(7);
console.log(smallCircle.getDiameter()); // 14
그런데 위에서 this가 가리키는 값은 함수 호출 방식에 의해 동적으로 결정된다고 했다. 직전에 살펴본 Circle 생성자 함수의 경우 this가 가리키는 값은 생성자 함수가 생성할 인스턴스를 가리켰는데, 아래와 같은 경우는 어떻게 다른지 살펴보자.
const circle = {
radius: 5,
getDiameter() {
return 2 * this.radius;
}
}
위와 같이 객체 리터럴의 메서드 내부에서 this가 사용된 경우, this는 메서드를 호출한 객체 (객체.메서드와 같이 호출할 것이므로 여기서는 circle)를 가리킨다.
정리하자면,
생성자 함수 내부에서 this가 사용된 경우, this는 생성자 함수가 생성할 인스턴스를
객체 리터럴의 메서드 내부에서 this가 사용된 경우, this는 메서드를 호출한 객체를 가리킨다.
자바스크립트 엔진은 this를 암묵적으로 생성하기 때문에 코드 어느 곳에서나 this를 참조할 수 있다.
객체의 메서드나 생성자 함수 내에서 사용된 this가 아니라면, this는 전역객체 window 또는 undefined 가 바인딩 된다.
위치 | 생성자 함수 내부 | 객체리터럴의 메서드 내부 | 전역 | 일반 함수 내부 |
this에 바인딩된 값 | 생성할 인스턴스 | 메서드를 호출한 객체 | window | strict mode? undefined : window |
끝.
Reference
모던 자바스크립트 deep dive :자바스크립트의 기본 개념과 동작 원리 /이웅모 지음.
'Frontend > javascript' 카테고리의 다른 글
[javascript] 생성자 함수는 어떤 과정으로 인스턴스를 생성할까? (2) | 2024.04.25 |
---|---|
[javascript] 생성자 함수에 의한 객체 생성 - 언제 필요하고 어떻게 사용하는가? (0) | 2024.04.18 |
자바스크립트 객체 프로퍼티 이해하기 2. [프로퍼티 정의] (0) | 2024.04.01 |
자바스크립트 객체 순회 메서드 : for...in / Object.keys() / Object.values() / Object.entries() / Object.getOwnPropertyNames() / Reflect.ownKeys() (0) | 2024.03.28 |
자바스크립트 객체 프로퍼티 이해하기 1. [내부 슬롯 & 내부 메서드 ] (0) | 2024.03.24 |
댓글