关于javascript:彻底深刻理解js原型链之prototypeproto以及constructor二

43次阅读

共计 3038 个字符,预计需要花费 8 分钟才能阅读完成。

前言

如果你可能啃下教程一并且吃透原型链的几个概念的话阐明你在前端飞仙的路上又进了一小步···学习最怕的不是慢而是站!这篇教程次要目标对原型链概念进一步加深了解

坚固下教程一的常识

来看上面的例子:

var text=new String("我是文字");
function Persion(name,job){
    this.name=name;
    this.job=job;
}
Persion.myName="lxm";
Persion.prototype.sayName=function(){alert(this.name);}
var perison1=new Persion("lxm","20")

思考:判断下列表达式返回的值:

(两分钟之内对八道的算及格,剩下的同学回头接着了解教程一,传送门在此 [http://0313.name/2017/01/13/p…])

perison1.__proto__===Persion.prototype;
perison1.name===Persion.name;
perison1.prototype.__proto__===Object.prototype;
Persion.prototype.__proto__===Object.prototype;
Persion.__proto__===Function.prototype;
Persion.constructor===perison1;
Function.__proto__===Object.prototype;
Function.prototype.__proto__===Object.prototype;
typeof Persion.prototype;
typeof Function.prototype;

原型链图

这个图相对是网络上举世无双独一份,此乃小米飞升教程独家秘籍!因为博主在学习过程中发现对文字的了解和记忆远远不如一个图来的更深更直观,更加透彻, 为了您更好的学习原型链,博主特意花了一上午的工夫用 mermaid 绘制了这个原型链的关系图,而且通过这个图咱们可能发现很多有意思的事件
为了关系图更加直观和清晰,隐去了一些援用线路,其中:

  • 圆形代表对象的名字
  • 方形代表属性名
  • 实线代表对象的分界
  • 虚线代表援用
  • 菱形代表根本值

  1. 原型链是单链,只往一个方向流向,没有回路
  2. 只有 Function 的__proto__指向本人的 prototype,这也向咱们解释了为什么 Function.prototype 类型是 function
  3. 咱们通过__proto__只能获取到原型对象中的办法和属性,所以 persion1 通过原型链是获取不到 Persion 的 myName 属性,然而咱们能够通过原型对象的 constructor 来获取或者批改 Persion 的属性(这点太给力了)

请留神,有时候这个办法也不好使,因为原型对象的 constructor 是能够扭转的,不肯定指向原型对象所在的函数对象

持续下面的例子:

persion1.__proto__.constructor.myName="我变了耶!";
console.log(Persion.myName); // 我变了耶
  1. 一般对象的_proto__肯定指向发明它的函数对象的 prototype
  2. 原型对象的__proto__肯定指向 Object.prototype!
  3. 通过图咱们能够简略了解,领有原型对象属性的对象是函数对象,否则为一般对象
  4. 原型链是有开始和止境的,开始于 null,完结于一般对象
  5. 所有的函数对象都是 Function 以 new 的形式发明进去了,包含 Function 本人且每个函数对象的__proto__都指向了 Function.prototype
  6. Object 是所有对象的父类,咱们也能够称之为基类,不过不要纠结于叫什么,因为咱们通过图能够看到每一个对象(不论是原型对象还是一般对象还是函数对象)的通过原型链都能够引向 Object.prototype

以上九条我称为原型链之九句真言(不要太在意名字,我本人轻易起的 ~)

意外播种:this.name 和 this.job 难道不应该在 Persion 中也有一份吗?无数个日夜,愚蠢的博主对 this 的用法都不甚了解,直到我画出了这种图,我 tm 彻底明确了 this 的含意,就是谁运行蕴含 this 的这个函数,this 就把挂在它身上的包袱(属性)甩给谁!
看到了吗,persion1 调用了 Persion,那么天然多了 2 个属性,然而留神,name 跟 job 并不是 Persion 的属性!!

思考:图中没有画出 Object.__proto__的指向,请问他指向哪?(请只根据九句真言解答)

思考题解答

思考:判断下列表达式返回的值:

perison1.__proto__===Persion.prototype;

首先判断 perison1 是通过 new 形式被 Persion 发明进去的,根据九句真言第 4 条得出:true

perison1.name===Persion.name;

通过关系图能够看到不相等,我曾经在意外播种中解答了,答案为:false

perison1.prototype.__proto__===Object.prototype;

只看图能够看到 perison1 没有 prototype,是一般对象所以答案为:js 报错~~

Persion.prototype.__proto__===Object.prototype;

参考九句真言第 5 条:答案为:true

Persion.__proto__===Function.prototype;

Persion 为函数对象,参考九句真言第 8 条,答案为:true

Persion.constructor===perison1;

Persion 是由 Function 发明进去的所以 Persion.constructor 指向 Function,答案为:false

Function.__proto__===Object.prototype;

Function 咱们曾经反复强调是由本身发明所以 Function.__proto__===Function.prototype;, 答案为:false

Function.prototype.__proto__===Object.prototype;

依据九句真言第 5 条,答案为:true

typeof Persion.prototype;

答案为:object

typeof Function.prototype;

答案为:function, 留神这个是比拟非凡的原型对象

思考:图中没有画出 Object.__proto__的指向,请问他指向哪?(请只根据九句真言解答)

上面来分步解答

  1. Object 属于函数对象
  2. 根据九句真言第八条得出函数对象的__proto__都指向了 Function.prototype
  3. 所以 Object.__proto__===Function.prototype

这一点是不太好了解的,是 Function 发明了 Object, 而后 Object 发明了 Function 的原型对象 prototype
所以就有了

Object.__proto__===Function.prototype
Function.prototype.__proto__===Object.prototype

不要太纠结于此,只有了解就好

结束语

好了,原型链的概念原理通过这 2 篇教程我置信大家曾经滚瓜烂熟了!上面的教程,咱们会着重钻研下原型链在理论的利用!

作者 宜信技术学院 刘晓敏

正文完
 0