对于新手来说,JavaScript的原型是一件很头疼的事情。一来prototype很容易和__proto__混淆【注意前面有两个_】,二来原来它们之间的各个方向真的很复杂。其实市面上已经有很多文章试图说清楚了。有一张所谓的经典图片,上面画了各种线条。说实话,我当时看得头晕目眩,更谈不上完全理解了。所以我也想自己尝试一下,看看能不能把原型中的重要知识点分离出来,用最简单的图表形式解释清楚。我们知道原型是一个对象,其他对象可以通过它实现属性继承。但是除了原型之外,另一个__proto__是用来做什么的呢?长得那么像,人家怎么能分得清呢?他们指的是谁,又怎么会记错了呢?原型链是什么鬼?相信很多初学者甚至有一定经验的老手都未必能够完全解释清楚。下面是三张简单的图片和一些示例代码来理解。vara={};console.log(a.prototype);//undefinedconsole.log(a.__proto__);//Object{}varb=function(){}console.log(b.prototype);//b{}console.log(b.__proto__);//function(){}/*1,文字方法*/vara={};console.log(a.__proto__);//对象{}console.log(a.__proto__===a.constructor.prototype);//true/*2,构造方法*/varA=function(){};vara=newA();console.log(a.__proto__);//A{}console.log(a.__proto__===a.constructor.prototype);//true/*3,Object.create()方法*/vara1={a:1}vara2=Object.create(a1);console.log(a2.__proto__);//Object{a:1}console.log(a.__proto__===a.constructor.prototype);//false(这里是图1的异常)varA=function(){};vara=newA();console.log(a.__proto__);//A{}(构造函数A的原型对象)console.log(a.__proto__.__proto__);//对象{}(即is,构造函数的原型对象Object)console.log(a.__proto__.__proto__.__proto__);//null【本文为专栏作家“谢君”原创稿件,可通过作者微信转载公众号(jingfeng18)取得联系】点此查看作者更多好文
