1. 클래스와 생성자 함수의 차이
// 클래스
class DogCls {
constructor(name, breed) {
this.name = name;
this.breed = breed;
}
bark() {
return `${this.name} says woof`;
}
sleep() {
return `${this.name} is sleeping`;
}
}
const dog01 = new DogCls("asdf", "qwer");
const dog02 = new DogCls("ASDF", "QWER")
// 생성자 함수
function DogFn(name, breed) {
this.name = name;
this.breed = breed;
this.bark = function () {
return `${this.name} says woof`;
};
this.sleep = function () {
return `${this.name} is sleeping`;
};
}
const dog03 = new DogFn("1234", "4321")
const dog04 = new DogFn("!@#$", "$#@!")
객체 인스턴스를 생성하는 방법으로는 클래스를 이용하는 방벙과 생성자 함수를 이용하는 방법이 존재합니다. (위 코드)
하지만 두 방법에는 약간의 차이가 존재합니다.
- 클래스 이용
클래스(DogCls)를 이용하여 객체 인스턴스를 생성(dog01, dog02)할 때, bark와 sleep 메소드는
제일 처음 객체 인스턴스가 생성될 때 한번만 프로토타입에 추가됩니다.
즉, dog01로 bark를 접근하든, dog02로 bark를 접근하든 같은 메모리 주소를 참조하게되는 것입니다.
- 생성자 함수 이용
반면, 생성자 함수(DogFn)를 이용하여 객체 인스턴스를 생성(dog03, dog04)할 때, bark와 sleep 메소드는
각 객체 인스턴스가 생성될 때 각각 추가됩니다.
즉, dog03으로 bark를 접근할때와 dog04로 bark를 접근할때 참조하는 메모리 주소가 다릅니다.
그래서 이게 무슨 의미가 있나?
적은 수의 객체 인스턴스를 생성할 때에는 별 차이가 없을 수 있습니다.
하지만 만약 매우 많은 객체 인스턴스를 생성한다고 가정하면,
클래스를 이용하면 몇번 새롭게 객체 인스턴스를 생성해도 결국 하나의 메모리 주소를 참조합니다.
반면, 생성자 함수를 이용하면 수많은 메모리 주소가 복사되어 각각 참조될것이기 때문에 성능에 문제가 생길수있습니다.
2. 프로토타입이란?
위에서 클래스를 이용하여 객체 인스턴스를 생성하면, 프로토타입에 추가된다고 하였습니다.
여기서 말하는 프로토타입이란
자바스크립트의 모든 객체에 존재하는 프로토타입이라는 특별한 내장 속성으로, 객체가 다른 객체로부터 기능과 속성을 상속받을 수 있게 하는 기본 메커니즘입니다.
이러한 프로토타입에 최상위에는 Object.prototype(toString(), valueOf()....등)이 존재하며,
이 최상위 프로토타입을 시작으로 상위 객체에서 다른 객체로 상속이 이루어질 때,
하위 객체들은 이 프로토타입에 접근하여 상위 객체들의 기능과 속성에 접근할 수 있게됩니다.
class DogCls {
constructor(name, breed) {
this.name = name;
this.breed = breed;
}
bark() {
return `${this.name} says woof`;
}
sleep() {
return `${this.name} is sleeping`;
}
}
const dog01 = new DogCls("asdf", "qwer");
const dog02 = new DogCls("ASDF", "QWER")
dog01.bark() // "asdf says woof"
예시로 다시 살펴보면, dog01, dog02등의 객체 인스턴스가 상위 객체(DogCls)에 정의된 bark 메소드등에 접근 가능한 것은, 프로토타입에 저장되어있는 bark를 참조하기 때문에 가능한 것입니다.
function DogFn(name, breed) {
this.name = name;
this.breed = breed;
this.bark = function () {
return `${this.name} says woof`;
};
this.sleep = function () {
return `${this.name} is sleeping`;
};
}
const dog03 = new DogFn("1234", "4321")
const dog04 = new DogFn("!@#$", "$#@!")
dog03.bark() // "1234 says woof"
반면, 생성자 함수를 이용해서 객체 인스턴스를 생성해도 메소드에 접근 가능하지만,
이것은 프로토타입에 저장된 메소드를 참조하는게 아닌,
객체 인스턴스가 생성될 때 복사해온 새로운 주소의 메소드를 참조하고 있는 것입니다.
만약 생성자 함수에서도 프로토타입을 활용하고싶다면, 아래와 같이 조절해볼수있습니다.
function DogFn(name, breed) {
this.name = name;
this.breed = breed;
}
DogFn.prototype.bark = function() {
return `${this.name} says woof`;
};
DogFn.prototype.sleep = function() {
return `${this.name} is sleeping`;
};
const dog03 = new DogFn("1234", "4321");
const dog04 = new DogFn("!@#$", "$#@!");
'OLD > Javascript' 카테고리의 다른 글
[Javascript] this 키워드 알아보기 (0) | 2024.03.24 |
---|---|
[Javascript] 자바스크립트 프로토타입(Prototype) (0) | 2023.03.01 |
[Javascript] 자바스크립트 비동기(Async)_02 (콜백 지옥(Callback Hell), 프로미스(Promise), async/ await... ) (0) | 2023.02.28 |
[Javascript] 자바스크립트로 브라우저 저장소 이용하기 (LocalStorage, Cookies, indexedDB) (0) | 2023.02.27 |
[Javascript] 자바스크립트 모듈 (0) | 2023.02.26 |