关于javascript:一题搞懂原型链

37次阅读

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

原型链类型的题在面试中属于高频考点,上面用一个经典的面试题还原 js 中原型链的真面目。

请问:f 有办法 a 和办法 b 吗?

var F = function () {};Object.prototype.a = function () {};Function.prototype.b = function () {};var f = new F()

在做这题之前,肯定要理解 js 中原型链的一些继承关系,把那种继承关系图记在脑子里,而后看到题目后把各自一一对应寻找继承关系,之前走过弯路,初学 js 时在网上找原型链的图,又简单又记不住,相似这种:

不要看了,反正我是看不下去。

正言

在 js 中,对象都有__proto__属性,个别这个是被称为隐式原型,该隐式原型指向结构该对象的构造函数的原型。
函数比拟非凡,它除了和其余对象一样有__proto__属性,还有本人特有的属性 —-prototype,这个属性是一个指针,指向一个蕴含所有实例共享的属性和办法的对象,称之为原型对象。原型对象也有一个 constructor 属性,该属性指回该函数。

依照上述的实践能够把构造函数(函数)、对象(构造函数 new 进去的)、Object(顶层的对象)之间的大略关系串起来。相似如下:

这张图是我在吴华的 javascript 高级进阶课程中看到的截图,受用至今。
记住这四个最次要的点就 ok 了,对照上图了解记忆:

  1. 对象都有个 隐式原型__proto__), 它指向构造函数的原型对象(prototype)。
  2. 构造函数的原型对象也有个 隐式原型 __proto__)它指向Object 的原型对象(prototype).
  3. Object的原型对象有个 constructor 指向 Object 自身。
  4. 构造函数的 constructor 指向构造函数自身。

这里看完你就能明确对象上的 toString() 或者 valueof() 是怎么来的了,打印一下 Object 的原型对象,就能失去后果,你去拜访对象的属性(包含办法),他会先找本身有没有这个属性,没有的话会沿着原型链一层一层往上找,例如上图,我要拜访 objshowAge办法,他自身有,返回他自身的 showAge 办法,要拜访 showUserNameobj 没有,会沿着隐式原型去看看构造函数的原型对象有没有,有的话返回,没有的话持续去 Object 的原型对象去找,顺次往上。这也不难理解为什么对象上都有 toString() 办法了。

解题思路

了解原型链后,再回到最后的那道面试题:

  1. 首先,f 是什么?
    f 是构造函数 F new 进去的对象,依照下面我说的,对象都有个隐式原型,它指向构造函数的原型对象,即 f 的__proto__指向 F.prototype。
  2. 沿着原型链,F.prototype.__proto__指向 Object.prototype,即得出第一个答案了,f 能够取到 a 办法,因为 f 的原型链上没通过 Function.prototype,Function.prototype 是 Object.prototype 创立的,只能沿着_proto_向上找所以取不到 b 办法。
  3. 函数都是由 Function new 进去的,这里你能够把它当成一个被另一个构造函数 new 进去的一般对象,所以 F 这个构造函数的隐式原型也指向了 Function 的原型对象,即 F.__proto__指向 Function.prototype,所以 F 函数能够取到 b 办法(可能有点晕,上面会解释)

Function

在 JavaScript 中,用 new 关键字来调用的函数,称为构造函数。构造函数首字母个别大写

那我了解的是实践上任何一个函数都能够当成一个构造函数。
其实下面的原型图还有一部分 Function 的没画进去。
理解这个之前,带着另一个面试题去思考:
原型链顶层是什么?依照下面的图你可能会认为是 Object 或者 Object.prototype, 其实不是。
留神:

要了解原型链顶层要和原型链其余中央的了解有一些不同,这里 Object 和 Function 及其原型要离开看,不能将原型和自身看作是天经地义的关系

  1. Object.prototype 和 Object 的关系
    Object.prototype 是 JS 世界中最早生成的,实践上有了原型(Object.prototype) 就会有自身(Object),然而 Object 的内容却是由 Function 形成的。用艰深一点的话来解释就是,有了 Object.prototype 就有了 Object 的精神,然而 Object 的灵魂却是由 Function 形成的。
  2. Object.prototype.__proto__
    Object.prototype 是由下层对象创立的 (一些动态语言,像 C ++ 和 Java),在这里为了不引起误会将其指向了 null

总结原型链顶层关系

  1. Object.prototype 是由下层对象创立的 (一些动态语言,像 C ++ 和 Java),在这里为了不引起误会将其指向了 null
  2. Object.prototype 发明了 Function.Prototype
  3. Function.prototype 发明了 Function
  4. Object 发明了其余对象(window, document, 自定义对象)
  5. Object 是 Function 的一个实例
  6. 任何函数继承自 Function.prototype
  7. 任何对象最终继承自 Object.prototype

正文完
 0