JavaScript高级②|原型与原型链,一张图彻底搞懂

张开发
2026/6/5 19:56:15 15 分钟阅读

分享文章

JavaScript高级②|原型与原型链,一张图彻底搞懂
author: 专注前端开发分享JavaScript干货title: JavaScript高级②原型与原型链一张图彻底搞懂update: 2026-04-28tags: JavaScript,原型,原型链,proto,prototype,继承,前端进阶作者专注前端开发分享JavaScript干货更新时间2026年4月适合人群有JS基础想理解对象模型和继承的开发者前言为什么需要原型JavaScript 没有传统类的概念而是通过**原型prototype**实现对象之间的共享和继承。不懂原型JS的对象系统就是黑盒。一、原型的两个核心规则1.1 prototype 与proto// 规则1函数有 prototype 属性functionPerson(name){this.namename;}console.log(Person.prototype);// { constructor: Person, ... }// 规则2对象有 __proto__ 属性指向它的原型constpnewPerson(张三);console.log(p.__proto__Person.prototype);// true ✅// 规则3原型对象也有 __proto__最终指向 nullconsole.log(Person.prototype.__proto__Object.prototype);// trueconsole.log(Object.prototype.__proto__);// null 原型链终点1.2 一张图看懂原型链实例对象 p ↓ __proto__ Person.prototype ↓ __proto__ Object.prototype ↓ __proto__ null 终点二、属性查找机制访问对象属性时JS会沿着原型链向上查找直到 null。functionPerson(name){this.namename;}// 在原型上添加方法所有实例共享Person.prototype.sayHifunction(){console.log(你好我是${this.name});};constp1newPerson(张三);constp2newPerson(李四);p1.sayHi();// 你好我是张三 从 p1.__proto__ 找到p2.sayHi();// 你好我是李四// 查找顺序演示constobj{};console.log(obj.toString());// 来自 Object.prototype// obj 自身没有 toString// → obj.__proto__ (Object.prototype) 找到了三、constructor 属性functionPerson(){}constpnewPerson();console.log(Person.prototype.constructorPerson);// trueconsole.log(p.constructorPerson);// true// p自身没有constructor从 p.__proto__ (Person.prototype) 找到// 重写 prototype 时要修正 constructorPerson.prototype{// constructor: Person, // ❌ 忘记写这个sayHi(){console.log(hi);}};constp2newPerson();console.log(p2.constructorPerson);// false ❌指向了Objectconsole.log(p2.constructorObject);// true// ✅ 正确做法Person.prototype{constructor:Person,// 手动修正sayHi(){console.log(hi);}};四、原型链继承4.1 传统继承方式// 父类functionAnimal(name){this.namename;}Animal.prototype.eatfunction(){console.log(${this.name}在吃东西);};// 子类functionDog(name,breed){Animal.call(this,name);// 调用父类构造函数this.breedbreed;}// 设置原型链Dog.prototypeObject.create(Animal.prototype);Dog.prototype.constructorDog;// 修正constructor// 子类方法Dog.prototype.barkfunction(){console.log(${this.name}在汪汪叫);};constdognewDog(旺财,金毛);dog.eat();// 旺财在吃东西 来自Animal.prototypedog.bark();// 旺财在汪汪叫 来自Dog.prototype4.2 ES6 class 语法语法糖classAnimal{constructor(name){this.namename;}eat(){console.log(${this.name}在吃东西);}}classDogextendsAnimal{constructor(name,breed){super(name);// 调用父类构造函数this.breedbreed;}bark(){console.log(${this.name}在汪汪叫);}}constdognewDog(旺财,金毛);dog.eat();// 旺财在吃东西dog.bark();// 旺财在汪汪叫console.log(doginstanceofDog);// trueconsole.log(doginstanceofAnimal);// true五、instanceof 原理// instanceof 检查原型链functionPerson(){}constpnewPerson();console.log(pinstanceofPerson);// true// 检查p.__proto__ Person.prototype → trueconsole.log(pinstanceofObject);// true// 检查p.__proto__.__proto__ Object.prototype → true// 手写 instanceoffunctionmyInstanceof(obj,Constructor){letprotoobj.__proto__;while(proto){if(protoConstructor.prototype){returntrue;}protoproto.__proto__;}returnfalse;}六、原型污染与安全问题// 原型污染修改 Object.prototype 会影响所有对象Object.prototype.isAdmintrue;constobj{};console.log(obj.isAdmin);// true ❌ 所有对象都有了// 安全做法用 Object.create(null) 创建无原型对象constsafeObjObject.create(null);safeObj.name张三;console.log(safeObj.toString);// undefined 没有原型链七、知识卡概念说明prototype函数的属性用来共享方法__proto__对象的属性指向原型原型链对象查找属性的路径constructor指向构造函数instanceof检查是否在原型链上Object.create()创建指定原型的对象classES6 继承语法糖八、课后作业画出const arr []的原型链图实现一个new的模拟函数myNew(Constructor, ...args)用原型链方式实现父类Vehicle子类Car继承并添加drive方法有问题欢迎评论区留言大家一起讨论标签JavaScript | 原型 | 原型链 |proto| prototype | 继承 | 前端进阶

更多文章