[Javascript] Class
JS Class, JavaScript class, ES6 class
정의
ES6 class 는 prototype chain 위의 문법 설탕. C++/Java 스타일 OOP 와 닮았지만 내부는 JS Prototype Chain.
class Animal {
constructor(name) {
this.name = name;
}
speak() { return `${this.name} makes a sound`; }
static create(name) { return new Animal(name); }
}
const a = new Animal('Cat');
a.speak(); // 'Cat makes a sound'
Animal.create('Dog'); // static
구조
class Foo {
// 인스턴스 필드
x = 0;
// 정적 필드
static y = 1;
// private 필드 (ES2022)
#secret = 42;
static #STATIC_SECRET = 99;
constructor(arg) { ... }
method() { ... }
static staticMethod() { ... }
get prop() { return this.x; }
set prop(v) { this.x = v; }
static {
// static initialization block (ES2022)
Foo.y = compute();
}
}
상속
class Dog extends Animal {
constructor(name, breed) {
super(name); // 부모 constructor
this.breed = breed;
}
speak() {
return super.speak() + ' (woof)';
}
}
super 의 의미
super(...): 부모 constructor 호출super.method(): 부모 메서드 (현재 this 로)
자식 constructor 에서 super() 호출 전에 this 접근 시 ReferenceError.
private (ES2022)
class Counter {
#count = 0;
increment() {
this.#count++;
}
get value() {
return this.#count;
}
}
const c = new Counter();
c.#count // ❌ SyntaxError (외부 접근 불가)
# prefix 가 진짜 private. Symbol 흉내가 아닌 언어 차원의 강제.
static 메서드 / 필드
class MathUtils {
static PI = 3.14159;
static circle(r) {
return MathUtils.PI * r * r;
}
}
MathUtils.circle(5); // ✓
new MathUtils().circle(5); // ❌ (인스턴스에는 없음)
getter / setter
class Temperature {
#celsius = 0;
get fahrenheit() { return this.#celsius * 9/5 + 32; }
set fahrenheit(f) { this.#celsius = (f - 32) * 5/9; }
}
const t = new Temperature();
t.fahrenheit = 100;
t.fahrenheit; // 100
class expression
const MyClass = class {
method() { ... }
};
const Named = class FooClass {
// FooClass 는 내부에서만 사용 가능
};
instanceof
const d = new Dog();
d instanceof Dog // true
d instanceof Animal // true (chain)
d instanceof Object // true
class vs function
| function constructor | class | |
|---|---|---|
| 호이스팅 | ✓ (var 처럼) | ✗ (TDZ) |
| 호출 | new Foo() 또는 Foo() | new 필수 |
strict mode | 명시 | 자동 |
super | 직접 구현 어려움 | 자연스러움 |
// function 으로 같은 동작
function Animal(name) {
this.name = name;
}
Animal.prototype.speak = function() { ... };
class 가 깔끔하고 권장.
자주 만나는 패턴
추상 클래스 흉내
class Shape {
constructor() {
if (new.target === Shape) {
throw new Error('Shape is abstract');
}
}
area() { throw new Error('Must implement'); }
}
class Circle extends Shape {
constructor(r) { super(); this.r = r; }
area() { return Math.PI * this.r ** 2; }
}
mixin
const Serializable = Base => class extends Base {
toJSON() { return JSON.stringify(this); }
};
class User extends Serializable(Object) {
constructor(name) { super(); this.name = name; }
}
함수가 class 를 받아 새 class 반환.
함정
1. 호이스팅 안 됨
new Foo(); // ❌ ReferenceError
class Foo {}
2. this 바인딩
class Foo {
method() { return this.x; }
}
const f = new Foo();
const m = f.method;
m(); // this 가 undefined (strict 자동)
해법: bind 또는 arrow function 필드.
class Foo {
method = () => this.x; // bound to instance
}
3. new 없이 호출 금지
class Foo {}
Foo(); // ❌ TypeError
4. extends null
class Foo extends null { ... }
// Object.prototype 도 상속 안 함, 거의 안 씀
참고
이 글의 용어 (3개)
- [Javascript] functionjavascript
- 정의 은 JavaScript 에서 함수를 만드는 가장 기본적인 키워드. 호이스팅, 동적 바인딩, 객체, 호출 등 과 구분되는 고유한 특성을 가진다. 함수가 값 으로 다뤄지는 의 …
- [Javascript] Objectjavascript
- 정의 JavaScript 의 는 key-value 쌍의 컬렉션. 거의 모든 non-primitive 값이 객체. 함수, 배열, 정규식도 객체. 생성 접근 수정 / 삭제 Objec…
- [Javascript] Prototype Chainjavascript
- 정의 JavaScript 의 모든 객체는 (내부 슬롯) 을 가진다. 속성 lookup 시 자신에게 없으면 prototype chain 을 따라 올라가며 검색. 접근 함수의 pro…
💬 댓글