核心是将方法挂到构造函数的 prototype 上,使所有实例通过 proto 链共享同一份函数;错误写法在构造函数内定义方法导致重复创建,正确写法统一挂载 prototype 实现复用;继承通过 Object.setPrototypeOf 设置子类 prototype 指向父类 prototype;动态扩展原型可即时生效于已有实例;注意 constructor 与 proto 的区别,优先使用 Object.getPrototypeOf 和 Object.setPrototypeOf 等标准 API。

核心是把方法挂到构造函数的 prototype 上,让所有实例通过 __proto__ 链自动共享同一份函数,而不是每个对象自己存一份。
把公共方法写在 prototype 上
构造函数内部定义的方法属于实例私有,每次 new 都新建一个函数对象;而写在 prototype 上的方法只有一份,被所有实例引用。
- ❌ 错误写法(浪费内存):
function Person(name) {
this.name = name;
this.sayHi = function() { console.log('Hi ' + this.name); }; // 每个实例都新建函数
} - ✅ 正确写法(共享复用):
function Person(name) {
this.name = name;
}
Person.prototype.sayHi = function() { console.log('Hi ' + this.name); }; // 所有实例共用这个函数
const p1 = new Person('Alice');
const p2 = new Person('Bob');
p1.sayHi === p2.sayHi; // true
利用原型链向上查找实现继承式共享
子类实例不仅能访问自身构造函数 prototype 上的方法,还能沿原型链访问父类 prototype 的方法。
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
- 设置子类原型指向父类原型:
function Animal(name) { this.name = name; }
Animal.prototype.eat = function() { console.log(this.name + ' is eating'); };
function Dog(name, breed) {
Animal.call(this, name);
this.breed = breed;
}
// 关键:让 Dog 实例的 __proto__ 指向 Animal.prototype
Object.setPrototypeOf(Dog.prototype, Animal.prototype);
const dog = new Dog('Leo', 'Golden');
dog.eat(); // ✅ 可以调用 Animal.prototype.eat
运行时动态扩展,已有实例立即生效
因为实例只是“链接”到原型对象,不是拷贝,所以修改原型会实时影响所有已存在实例。
立即学习“Java免费学习笔记(深入)”;
- Person.prototype.walk = function() { console.log(this.name + ' is walking'); };
const p3 = new Person('Charlie');
p1.walk(); // ✅ 即使 p1 创建于 walk 添加之前,也能调用 - 注意:若实例自身已定义同名属性,会屏蔽原型上的值(即“属性遮蔽”),此时需用
delete p1.sayHi才能重新访问原型版本。
避免常见陷阱:constructor 和 __proto__ 不要混用
prototype 是函数才有的属性,__proto__ 是对象才有的内部链接。不要试图给普通对象直接赋值 __proto__ 来模拟继承(兼容性和可维护性差)。
- 推荐方式获取/设置原型:
Object.getPrototypeOf(p1) // 安全读取
Object.setPrototypeOf(Dog.prototype, Animal.prototype) // 安全设置 - __proto__ 是历史遗留接口,仅用于调试或极简场景;生产代码优先使用标准 API。

















