唯心主义蠢货的[js知识总结] 原型和原型链、类型判断

199 阅读3分钟

原型和原型链、类型判断

js原型的出现

在这里插入图片描述

1.构造函数

js设计之初,是作为提供网络交互的简易脚本语言,设计者并未想设计类,但需要有一种机制将所有对象联系起来,设计者借用了new关键字,但后边跟的并不是类名,而是直接的构造函数

function test(){  // 实际上这样就定义了一个构造函数
	this.name = "test"
}
let x = new test() // new对象后边跟的是构造函数

2.prototype

但是这样出现的问题是:无法共享属性,即每个对象都会有自己的属性和方法,无法提取共同部分进行复用,因此js设计者提出用prototype的方式,将需要共享的属性方法放在prototype中,不需要共享的则放在构造函数。

大概的思路是:我没必要单独搞一个类出来,但是只要我想我就可以共用一些东西

function dog(name){
	this.name = name;
}
dog.prototype.getName = function(){
	console.log(this.name);
}
let dog1 = new dog("哈士奇");

3.原型链

因此新建的对象由两个部分组成自己的属性和对应prototype的属性,而对应prototype的属性即为每个对象都用于的__ proto _ _, 他指向构造函数的prototype,即dog1. __ proto _ _ == dog.prototype

由于dog.prototype本身也是由构造函数new出来的,所以他本身作为一个对象也会有__ proto _ ,同时其内部有一个constructor属性,指向构造函数,构造函数的 __ proto __ 指向function.prototype

并且原型链是指对象的原型链,原型链上所有节点都是对象,不能是基本值,所以最后的节点应该为null,玄学一点的说法是所有事情都是从无到有(手动狗头)

即有两条原型链

(1)

dog.prototype._ _ proto_ _ _ == Object.prototype Object.prototype._ _ proto_ _ = null

(2)

dog.prototype.constructor._ _ proto_ _ == Function.prototype Function.prototype._ _ proto_ _ = Object.prototype Object.prototype._ _ proto_ _ = null

在这里插入图片描述
在这里插入图片描述

js类型判断

type of

可以利用 typeof 来判断number, string,object, boolean, function, undefined, symbol 这七种类型,

但type of并不能够直接判断出这个数据具体是那种object,以下是原理:

  • 000:对象
  • 010:浮点数
  • 100:字符串
  • 110:布尔
  • 1:整数

but, 对于 undefinednull 来说,这两个值的信息存储是有点特殊的。

null:所有机器码均为0

undefined:用 −2^30 整数来表示

因此 null在被判断时就会被判断为对象,

所以当我们使用typeof时最好用他来判断基本类型,避免对null的判断

instance of

instanceof 主要的作用就是判断一个实例是否属于某种类型,也可以判断一个实例是否是其父类或者祖先类的实例。

以下为大概的代码思路:

function test_Instance(leftValue,rightValue){
	let right = rightValue.prototype;
	let left = leftValue.__proto__;
	while(true){
		if(left == null){
			return false;
		}
		if(left == right){
			return true;
		}
		left = left.__proto__;// 向上查找对象的__proto__属性,
	}
}

判断当前所在层级的原型是否为要判断的原型,如果不是,则向上查找,进行遍历,如果是,则返回true

比较好的办法;

以下为较为准确的办法:

Object.prototype.toString.call(1) // "[object Number]"

Object.prototype.toString.call('hi') // "[object String]"

Object.prototype.toString.call({a:'hi'}) // "[object Object]"

Object.prototype.toString.call([1,'a']) // "[object Array]"

Object.prototype.toString.call(true) // "[object Boolean]"

Object.prototype.toString.call(() => {}) // "[object Function]"

Object.prototype.toString.call(null) // "[object Null]"

Object.prototype.toString.call(undefined) // "[object Undefined]"

Object.prototype.toString.call(Symbol(1)) // "[object Symbol]"

根据原型链向上查找

参考文章:

  1. Javascript继承机制的设计思想:www.ruanyifeng.com/blog/2011/0…

  2. 浅谈 instanceof 和 typeof 的实现原理https://juejin.cn/post/6844903613584654344#heading-0