JS原理解析——关键字instanceof

·  阅读 73
JS原理解析——关键字instanceof

一、话题引入

上一篇文章笔者浅谈了一下JS原型链,在此我想再阐述一个观念,笔者认为:真要探究JSFunctionObject的具体关系的话,就像是去探究到底是鸡生蛋和蛋生鸡的关系,实际上我们很难确定这两者:到底谁是谁的实例,谁是谁的构造函数,因此这两个JS内的关键字应该是同级的关系,至于原因嘛:

很喜欢Linux创始人Linus Torvalds大佬的那句话:Talk is cheap. Show me the code.

为了方便大家理解,我在这里先引用一下MDN上instanceof的定义
instanceof 运算符用于检测构造函数的 prototype 属性是否出现在某个实例对象的原型链上

  console.log(Object instanceof Function);
  console.log(Function instanceof Object);
复制代码

看到这里,不知道各位心中是否已经输出了两行代码的结果,其实我刚才已经说明了结果,接下来请让我解释一下原因:

二、instanceof原理解析

我们当然没法创造出一个类似instanceof的内部关键字来实现这个功能,但是我们可以使用函数来模拟这个过程。
简单地讲,instanceof的原理就如定义所说:在检测对象的原型链上面查找构造函数的prototype属性是否出现,这个过程会沿着原型链一直找,直到找到原型链的最顶端Object.prototype还没找到,那就只能返回null了,说明该对象不是这个构造函数的实例.

  //  instance_of这个函数就是我们用来模拟instanceof功能的函数
  //  它接收两个参数,第一个是检测的对象obj,第二个是检测的构造函数constructor
  function instance_of(obj, constructor) {
    let prototype = constructor.prototype;
    //  这里使用了一个定义在Object上面的API => getPrototypeOf
    //  它用于返回当前对象的原型的值
    let proto = Object.getPrototypeOf(obj);
    while(true) {
      //  如果查找完整个原型链还找不到prototype属性那么就返回null
      if(proto === null) {
        return false;
      } 
      //  这里就是对比当前原型对象上是否含有构造函数的prototype属性来判断结果,是则返回true循环结束
      else if(proto === prototype) {
        return true;
      }
      // 每一次循环都会返回当前对象的原型对象
      // 第一次当然是返回传入参数obj的原型对象,往后就是原型链上的每一个对象
      proto = Object.getPrototypeOf(proto);
    }
  }
  // 我们可以观察自己模拟的方法instance_of和系统内的方法instanceof对于这两个关键字的测试结果
  console.log(instance_of(Function, Object));
  console.log(instance_of(Object, Function));
  console.log(Function instanceof Object);
  console.log(Object instanceof Function);
复制代码

至于四行输出的结果,当然是四个true了,大家可以到浏览器的控制台试一试效果

三、总结

以上内容就是笔者对于instanceof原理的理解了,如果哪里有什么问题,希望大佬们多多指正,感谢!

分类:
前端
标签:
分类:
前端
标签:
收藏成功!
已添加到「」, 点击更改