객체 프로토타입 얻기와 설정하기
Object.getPrototypeOf(o)
를 통해 객체의 프로토타입을 얻을 수 있다.- ES5의
obj.__proto__
와 같다.
- ES5의
Object.setPrototypeOf(obj, proto)
를 통해 객체의 프로토타입을 설정할 수 있다.- ES5의
obj.__proto__ = proto
와 같다.
- ES5의
ES5 예제 소스코드
const proto = {
greet() {
console.log(`proto greet, name = ${this.name}`);
},
};
const obj = Object.create(proto);
console.log(obj.__proto__); // {greet: ƒ}
obj.name = "Joe";
obj.greet(); // proto greet, name = Joe
- 기존의
__proto__
는 deprecated 되었으므로, 더이상 사용하지 않는 것이 좋다.
ES6 이후 예제 소스코드
const proto = {
greet() {
console.log(`proto greet, name = ${this.name}`);
},
};
const obj = Object.setPrototypeOf({}, proto);
console.log(Object.getPrototypeOf(obj)); // {greet: ƒ}
obj.name = "Joe";
obj.greet(); // proto greet, name = Joe
- ES5 에서는
Object.create()
를 사용하거나obj.__proto__
에 직접 할당해야 했는데 ES6에서 공식적인 스펙이 생겼다. Object.setPrototypeOf(obj, proto)
는 기존의obj.__proto__ = proto
를 대체한다.
공식 스펙이 되었지만, 아이러니하게도 공식문서에서는 기존 객체의 프로토타입을 변경하면 퍼포먼스에 안좋을 수 있으니 퍼포먼스를 고려한다면,
Object.create()
로 새로운 프로토타입을 가진 새로운 객체를 생성하라고 경고하고 있다.
__proto__
를 사용하면 안되는 이유
- 브라우저가 아닌 자바스크립트 엔진에서는 공식 스펙이 아니다.
- 물론 지원할 수도 있다.
__proto__
는Object.prototype
에 의해 정의된 접근자 속성이어서 객체가Object.prototype
을 상속하지 않았다면 사용할 수 없다.
Object
를 상속하지 않고 __proto__
를 사용하는 경우
const proto = {
hello() {
console.log("hello");
},
};
const obj = Object.create(null);
obj.__proto__ = proto;
console.log(obj.hello()); // Uncaught TypeError: obj.hello is not a function
- 메서드 호출 시 에러가 난다.
Object
를 상속하지 않았지만, Object.setPrototypeOf()
를 사용하는 경우
const proto = {
hello() {
console.log("hello");
},
};
const obj = Object.create(null);
Object.setPrototypeOf(obj, proto);
console.log(obj.hello()); // hello
Object
를 상속하지 않았지만, 메서드 호출 시 에러가 발생하지 않는다.
반응형
'자바스크립트 > 모던 자바스크립트' 카테고리의 다른 글
ES6 이후에 새롭게 정의된 Object 편의 정적 메서드들 (0) | 2023.01.30 |
---|---|
모던 자바스크립트, 메서드 정의 문법과 super, [[HomeObject]] (0) | 2023.01.25 |
모던 자바스크립트, 단축 속성 (shorthand properties) (0) | 2023.01.24 |
모던 자바스크립트, 계산된 속성 이름 (computed property name) (0) | 2023.01.24 |
모던 자바스크립트, 심볼 (Symbol) (0) | 2022.12.23 |