빈 객체를 표현해보자
let obj = {};
alert(obj); // "[object Object]"
obj
는 비어있는데 [object Object]
문자열을 생성하는 코드는 어디에 있는걸까?
obj = new Object()
를 줄이면 obj = {}
가 된다
여기서 Object
는 내장 객체 생성자 함수인데, 이 생성자 함수의 prototype
은 toString
을 비롯한 다양한 메서드가 구현되어있는 거대한 객체를 참조한다
new Object()
를 호출하거나 리터럴 문법 {...}
을 사용해 객체를 만들 때, 새롭게 생성된 객체의 [[Prototype]]
은 Object.prototype
을 참조한다
👉 obj.toString()
을 호출하면 Object.prototype
에서 해당 메서드를 가져온다
let obj = {};
alert(obj.__proto__ === Object.prototype); // true
alert(obj.toString === obj.__proto__.toString); // true
alert(obj.toString === Object.prototype.toString); // true
alert(Object.prototype.__proto__); // null
Array
, Date
, Function
같은 내장 객체들 역시 프로토타입에 메서드를 저장한다
배열 [1, 2, 3]
을 만들면 기본 new Array()
생성자가 내부에서 사용되기 때문에 Array.prototype
이 배열 [1, 2, 3]
의 프로토타입이 된다
👉 이런 내부 동작은 메모리 효율을 높여주는 장점이 있다
String.prototype
에 메서드를 하나 추가하면 모든 문자열에서 해당 메서드를 사용할 수 있다
String.prototype.show = function() {
alert(this);
};
'Bye Bye!'.show(); // Bye Bye!
프로토타입은 전역으로 영향을 미치기 때문에 프로토타입을 조작하면 충돌할 가능성이 높다
두 가지 라이브러리에서 동시에 String.prototype.show
메서드를 추가하면 한 라이브러리의 메서드가 다른 라이브러리의 메서드를 덮어 쓰기 때문이다
네이티브 프로토타입 변경을 허용하는 경우는 폴리필을 만들 때 뿐이다
폴리필을 직접 구현한 후 폴리필을 내장 프로토타입에 추가할 때만 네이티브 프로토타입을 변경하자
Number.prototype
, String.prototype
, Boolean.protoype
같은 메서드를 저장한다