什么是原型模式?JavaScript 实现一个原型模式的示例
·
什么是原型模式?
原型模式(Prototype Pattern)是一种创建型设计模式,它通过复制已有对象作为原型,复制(克隆)该原型来创建新对象,而无需重新初始化对象。新对象的属性和方法基于原型对象复制而来,既可以复用原型的功能,又可以在复制后修改自身属性,实现 “基于模板创建对象” 的效果。
在 JavaScript 中,原型模式是语言原生支持的核心模式(基于原型链实现),所有对象都有一个 prototype(原型),新对象可以通过原型链继承原型的属性和方法。
原型模式的核心角色
- 原型对象(Prototype):被复制的模板对象,定义了新对象的初始属性和方法。
- 客户端(Client):通过克隆原型对象创建新对象,并可根据需要修改新对象的属性。
JavaScript 实现原型模式的示例
JavaScript 中实现原型模式主要有两种方式:
- 利用
Object.create()方法(基于原型创建新对象)。 - 利用构造函数的
prototype属性(通过原型链继承)。
1. 基于 Object.create() 的克隆(简单原型模式)
Object.create(proto) 方法会创建一个新对象,其原型指向 proto(即新对象继承 proto 的属性和方法),适合快速克隆简单对象。
// 原型对象:定义基础属性和方法
const userPrototype = {
name: "默认用户",
age: 18,
greet() {
console.log(`Hello, 我是${this.name},今年${this.age}岁`);
},
// 克隆方法:返回基于自身的新对象
clone() {
// 使用 Object.create 克隆原型,继承属性和方法
const clone = Object.create(this);
// 深拷贝属性(避免引用类型共享)
if (this.address) {
clone.address = { ...this.address }; // 假设 address 是对象
}
return clone;
}
};
// 客户端:通过克隆原型创建新对象
const user1 = userPrototype.clone();
user1.name = "Alice";
user1.age = 25;
user1.address = { city: "北京" };
user1.greet(); // 输出:Hello, 我是Alice,今年25岁
const user2 = userPrototype.clone();
user2.name = "Bob";
user2.age = 30;
user2.address = { city: "上海" };
user2.greet(); // 输出:Hello, 我是Bob,今年30岁
// 验证:新对象的原型是 userPrototype
console.log(Object.getPrototypeOf(user1) === userPrototype); // 输出:true
console.log(user1.address === user2.address); // 输出:false(深拷贝避免引用共享)
2. 基于构造函数和原型链(经典原型模式)
JavaScript 中,构造函数的 prototype 属性是所有实例的原型,实例通过原型链继承原型上的方法,适合创建多个同类型对象。
// 构造函数:初始化实例的私有属性
function Car(brand, color) {
this.brand = brand;
this.color = color;
}
// 原型对象:定义共享的方法(所有实例复用)
Car.prototype = {
constructor: Car, // 修复 constructor 指向
drive() {
console.log(`${this.color}的${this.brand}正在行驶`);
},
honk() {
console.log(`${this.brand}鸣笛:嘀嘀!`);
},
// 克隆方法:基于当前实例克隆新对象
clone() {
// 使用构造函数创建新实例,复制当前实例的属性
const clone = new Car(this.brand, this.color);
// 继承原型方法(可选,因 new 操作已自动关联原型)
Object.setPrototypeOf(clone, Car.prototype);
return clone;
}
};
// 客户端:创建原型实例
const bmw = new Car("宝马", "白色");
bmw.drive(); // 输出:白色的宝马正在行驶
// 克隆原型实例
const bmwClone = bmw.clone();
bmwClone.color = "黑色"; // 修改克隆对象的属性
bmwClone.drive(); // 输出:黑色的宝马正在行驶
bmwClone.honk(); // 输出:宝马鸣笛:嘀嘀!
// 验证:克隆对象与原型实例共享原型方法
console.log(bmw.drive === bmwClone.drive); // 输出:true(方法复用)
console.log(bmw !== bmwClone); // 输出:true(不同实例)
代码说明
-
原型对象:
- 在
Object.create示例中,userPrototype是原型,定义了name、age等基础属性和greet方法,clone方法通过Object.create(this)克隆自身。 - 在构造函数示例中,
Car.prototype是所有Car实例的原型,drive、honk等方法定义在原型上,实现所有实例的方法复用。
- 在
-
克隆逻辑:
- 浅克隆:直接复制属性,若属性是引用类型(如对象、数组),克隆对象与原型会共享该引用(需注意副作用)。
- 深克隆:对引用类型属性递归复制(如示例中
address的深拷贝),避免共享引用。
-
JavaScript 原型特性:
- 新对象通过原型链继承原型的属性和方法,无需重复定义,节省内存。
- 修改原型的方法会影响所有基于该原型创建的对象(动态特性)。
原型模式的优势
- 性能优化:克隆对象比重新初始化对象更高效,尤其对于创建成本高的复杂对象。
- 灵活性高:新对象可在原型基础上修改属性,无需修改原型本身,实现 “定制化创建”。
- 简化创建:无需知道对象的创建细节,只需基于现有原型克隆,降低耦合。
适用场景
- 创建复杂对象:如配置对象、组件实例等,通过克隆原型避免重复初始化。
- 需要大量相似对象:如游戏中的敌人、列表中的条目,共享基础属性,仅修改差异部分。
- 动态扩展:在运行时动态修改原型,所有克隆对象会自动继承修改(利用原型链的动态性)。
原型模式是 JavaScript 的核心设计模式,理解它有助于掌握 JavaScript 的继承机制(原型链)和对象创建逻辑。日常开发中,Object.create、class 语法(本质是原型的语法糖)都是原型模式的具体应用。
更多推荐


所有评论(0)