클래스 정의
- 클래스는 객체(인스턴스)를 생성하기 위한 템플릿이다.
- 클래스는 선언식과 표현식으로 정의가 가능하다.
- 표현식으로 정의할 수 있는 이유는, 클래스가 값처럼(데이터처럼) 자유롭게 사용될 수 있는 일급 객체라는 것을 의미한다.
class Base {}
const Base = class {};
const Base = class
- 클래스 몸체에 정의할 수 있는 메서드의 종류는
constructor(생성자)
,프로토타입 메서드
,정적 메서드
3가지가 존재한다.
class Person{
// 생성자
constructor(name, age, gender) {
this.name = name;
this.age = age;
this.gender = age;
}
// 프로토타입 메서드
sayHi(){
return `hi, i'm ${this.name}`
}
// 정적 메서드
static sayHello(){
return "hello"
}
}
constructor
- 인스턴스를 생성하고 초기화하기 위한, 특수 메서드(생성자 함수)
- 이름 변경 X
- 내부에서 this에 프로퍼티를 추가함으로써, 인스턴스에 필요한 프로퍼티 추가 가능
- 클래스 내부 1개만 존재 가능, 생략 가능(생략을 할시,
constructor(){}
가 암묵적으로 정의) - ES6 이전의 생성자 함수에서처럼 내부에 원시값을 리턴할시 암묵적으로
this
가 반환되며, 명시적으로 다른 객체를 리턴할 경우 명시한 해당 객체가 반환
프로토타입 메서드
- 클래스 몸체에서 정의한 메서드는 인스턴스의 프로토타입에 존재하는 메서드로, 프로토타입 체인에 의해 상속받아 사용 가능
- 프로토타입 메서드 내부
this
는 인스턴스를 가리킴
정적 메서드
- 클래스의 메서드로서 호출하여 사용 가능(인스턴스에서의 호출 X)
- 정적 메서드 내부
this
는 클래스를 가리킴
클래스 호이스팅
- 클래스는 함수로 평가되며 클래스 선언문은 let과 const 키워드로 선언한 변수처럼 호이스팅이 일어난다. (선언 이전에 호출할 경우 참조 오류 발생)
// ReferenceError: Cannot access 'Person' before initialization
const person1 = new Person("neo", 10, "male")
class Person{
// 생성자
constructor(name, age, gender) {
this.name = name;
this.age = age;
this.gender = age;
}
// 프로토타입 메서드
sayHi(){
return `hi, i'm ${this.name}`
}
// 정적 메서드
static sayHello(){
return "hello"
}
}
클래스의 인스턴스 생성 과정
- 클래스의 인스턴스 생성 과정은, ES6 이전의 생성자 함수의 인스턴스 생성 과정과 동일하다.
class Person{
constructor(name, age, gender) {
// 1. 암묵적으로 인스턴스 생성(빈 객체)
// Person {...}
console.log(this)
// 2. this에 바인딩된 인스턴스 초기화
this.name = name;
this.age = age;
this.gender = age;
// 3. 완성된 인스턴스가 바인딩된 this, 암묵적 반환
}
}
상속에 의한 클래스 확장, super 키워드
extends
키워드를 통해 기존 클래스를 확장하여 사용이 가능하다.super
키워드 통해,constructor
내부에서는 수퍼 클래스(상속을 받는 부모 클래스)의constructor
를 호출하여 재사용 및 확장이 가능하며, 메서드 내부에서는 수퍼 클래스의 메서드를 상속받아 그대로 사용이 가능하다.- 상속을 받는 서브 클래스의
constructor
에서super
호출 전에는this
를 참조할 수 없다. (서브 클래스는 자신이 인스턴스를 직접 생성하지 않고 수퍼 클래스에게 인스턴스 생성을 위임하기 때문이다. 따라서 super의 호출이 없으면 인스턴스의 생성 자체가 불가하기에this
가 바인딩이 되지 않으므로 참조가 불가하다.)
// 수퍼 클래스
class SuperClass {
constructor(name,age) {
this.name = name;
this.age = age;
}
sayHi(){
return `super ${this.name}`
}
}
// SuperClass를 확장
class SubClass extends SuperClass {
// 기존 프로퍼티에 gender 프로퍼티 추가
constructor(name,age,gender) {
// super 키워드를 통해 인스턴스 프로퍼티 확장
super(name,age);
this.gender = gender;
}
sayHi(){
// 메서드 내부 super를 통해 수퍼 클래스의 메서드 사용 가능
return super.getSuperClassName()
}
}
const subClass = new SubClass("sub",18,"male")
console.log(subClass)
'JavaScript' 카테고리의 다른 글
[Record] | 이벤트 루프, 마이크로 태스크, 매크로 태스크 (0) | 2022.07.05 |
---|---|
[DeepDive] - 26장(ES6 함수의 추가기능) 필요 내용 정리 (0) | 2022.06.27 |
[DeepDive] - 23장(실행 컨텍스트) 필요 내용 정리 (0) | 2022.06.17 |
[DeepDive] - 20장(strict mode), 21장(빌트인 객체) 필요 내용 정리 (0) | 2022.06.14 |
[DeepDive] - 17장(생성자 함수에 의한 객체 생성) 필요 내용 정리 (0) | 2022.06.09 |