前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >面试官提问之:如何手动实现一下 instanceof的功能

面试官提问之:如何手动实现一下 instanceof的功能

作者头像
用户10106350
发布2022-10-28 18:00:51
1740
发布2022-10-28 18:00:51
举报
文章被收录于专栏:WflynnWebWflynnWeb

instanceof

用于检测构造函数的 prototype 属性是否出现在某个实例对象的原型链上。

  • 语法:object instanceof constructor
    • object:某个实例对象
    • constructor:某个构造函数

用来检测 constructor.prototype 是否存在于参数 object 的原型链上。

示例

代码语言:javascript
复制
// 定义构造函数
function C () {}
function D () {}
// 实例化一个 o 对象
var o = new C()
// true,true --> C.prototype 在 o 的原型链上
console.log(o instanceof C, o.__proto__ === C.prototype, '此时 o 的 __proto__:', o.__proto__, '此时 C 的 prototype:', C.prototype)
// false,false --> D.prototype 不在 o 的原型链上
console.log(o instanceof D, o.__proto__ === D.prototype)
// true true --> Object.prototype 在 o 的原型链上
console.log(o instanceof Object, o.__proto__.__proto__ === Object.prototype)
// 这时我们修改构造函数 C 的原型为一个空对象
C.prototype = {}
// 实例化一个 o2 对象
var o2 = new C()
// true --> C.prototype 在 o2 的原型链上
console.log(o2 instanceof C)
// false,C.prototype 指向了一个空对象,这个空对象不在 o 的原型链上.
console.log(o instanceof C, '此时 o 的 __proto__:', o.__proto__, '此时 C 的 prototype:', C.prototype)
console.log('此时 D 的 prototype:', D.prototype);
// 继承
D.prototype = new C()
console.log('此时 D 的 prototype:', D.prototype);
var o3 = new D()
// true, true --> 因为 o3 是 构造函数 D new 出来的实例对象,所以 D.prototype 一定在 o3 的原型链上
console.log(o3 instanceof D, o3.__proto__ === D.prototype)
// true --> 因为 C.prototype 现在在 o3 的原型链上
console.log(o3 instanceof C)
// true,true --> 上面的结果为什么为 true 呢,看如下代码,D.prototype 是 构造函数 C new 出来的实例对象,所以 C.prototype 一定在 D.prototype 的原型链上
console.log(o3.__proto__ === D.prototype, D.prototype.__proto__ === C.prototype);
// true 相当于如下代码
console.log(o3.__proto__.__proto__ === C.prototype);

运行结果如图所示

一些容易出错的点

代码语言:javascript
复制
var simpleStr = "This is a simple string"; 
var myString = new String();
var newStr = new String("String created with constructor");
var myDate = new Date();
var myObj = {};
var myNonObj = Object.create(null);

// 返回 false, simpleStr 并不是对象
simpleStr instanceof String;
// 返回 true
myString instanceof String;
// 返回 true
newStr instanceof String;
// 返回 true
myString instanceof Object;
// 返回 true
myObj instanceof Object;
// 返回 true
({}) instanceof Object;
// 返回 false, 一种创建非 Object 实例的对象的方法
myNonObj instanceof Object;
// 返回 false
myString instanceof Date;
// 返回 true
myDate instanceof Date;
// 返回 true
myDate instanceof Object;
// 返回 false
myDate instanceof String;

Object.create(null) 会造成创建的对象其 __proto__ 指向为空

instanceof 判断基本数据类型的方法

其实就是自定义 instanceof 行为的一种方式,这里将原有的 instanceof 方法重定义,换成了 typeof,因此能够判断基本数据类型。

代码语言:javascript
复制
class PrimitiveNumber {
  static [Symbol.hasInstance](x) {
    return typeof x === 'number'
  }
}
// true
console.log(111 instanceof PrimitiveNumber)

手动实现一下instanceof的功能

代码语言:javascript
复制
function copyInstanceof (source, target) {
    // 基本数据类型以及 null 直接返回 false
    if (!['function', 'object'].includes(typeof source) || source === null) return false
    // getProtypeOf 是 Object 对象自带的一个方法,能够拿到参数的原型对象
    let proto = Object.getPrototypeOf(source)
    while (true) {
        // 查找到尽头,还没找到
        if (proto == null) return false
        // 找到相同的原型对象
        if (proto == target.prototype) return true
        proto = Object.getPrototypeOf(proto)
    }
}
代码语言:javascript
复制
console.log(copyInstanceof("111", String)); // false
console.log(copyInstanceof(new String("111"), String)); // true
console.log(copyInstanceof(Date, Function)); // true
console.log(copyInstanceof(null, Object)); // false
本文参与 腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2022-04-08,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 WflynnWeb 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • instanceof
    • 示例
      • 一些容易出错的点
        • instanceof 判断基本数据类型的方法
          • 手动实现一下instanceof的功能
          领券
          问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档