JS原型和原型链

JS原型和原型链

1:使用class实现继承

比如说我们定义一个类,给你一个构造函数,在初始化的时候通过名字和分数对这个类进行初始化

我们也可以定义一个自我介绍的方法

class Student {
    constructor(name,score) {
        this.name = name;
        this.score = score;
    }
    introduse(){
        console.log(`我是${this.name},我考了${this.score}`)
    }
}
const std = new Student("ldz", 150)
console.log("student",std)
std.introduse()

在这里插入图片描述

比如这个时候我们再定义一个老师类

class Teacher {
    constructor(name,subject) {
        this.name = name;
        this.subject = subject;
    }
    introduse(){
        console.log(`我是${this.name},我考了${this.subject}`)
    }
}
const teacher = new Teacher("addam", "js")
console.log("teacher",teacher)
std.introduse()

这个时候这两个类都有name这个属性,我们就可以定义一个父类Person,我们定义Person有name属性,Person有个drink的喝水方法,然后学生类和老师类均继承Person

class Person {
    constructor(name) {
        this.name = name;
    }
    drink(){
        console.log(`我是人,我要喝水`)
    }
}

class Student extends Person{
    constructor(name,score) {
        super(name);
        this.score = score;
    }
    introduse(){
        console.log(`我是${this.name},我考了${this.score}`)
    }
}
const std = new Student("ldz", 150)
console.log("student",std)
std.introduse()
std.drink()
class Teacher extends Person{
    constructor(name,subject) {
        super(name);
        this.subject = subject;
    }
    introduse(){
        console.log(`我是${this.name},我考了${this.subject}`)
    }
}
const teacher = new Teacher("ldz", "js")
console.log("teacher",teacher)
teacher.introduse()
teacher.drink()

从上面代码可以看出,继承之后就可以直接使用父类的方法了,但是如果要在初始化时也初始化父类的某一变量,那么就需要使用super()关键字。

在这里插入图片描述

2:js原型

首先可以看到我们刚才console.log(“student”,std)输出的std只有name和score两个属性,那为什么会存在std.introduse()呢。

在这里插入图片描述

这个时候就不能忽略底下的__prito__,这个就被称为隐式原型。这个__prito__也是一个对象,他内部就有introduse。

在这里插入图片描述

那我们可以输出一下Student.peototype,可以发现输出也是两个方法,而且Student.peototype === student.__proto __

在这里插入图片描述

此时 student.__proto __ ===Student.peototype其实就是隐式原型等于显示原型。然后当我们在一个对象上查找属性和方法的时候,查不到就回去这个函数的隐式原型上查找。

在这里插入图片描述

3:JS原型链

先写一个teacher方法

class Person {
    constructor(name) {
        this.name = name;
    }
    drink(){
        console.log(`我是人,我要喝水`)
    }
}
class Teacher extends Person{
    constructor(name,subject) {
        super(name);
        this.subject = subject;
    }
    teach(){
        console.log(`我是${this.name},我教${this.subject}课程`)
    }
}
const teacher = new Teacher("ldz", "js")
console.log("teacher",teacher)
teacher.teach()
teacher.drink()

这个时候teacher构造成功之后执行了两个方法,一个是teacher.teach(),这个是在teach存在于teacher对象的隐式原型,也就是Teacher类的显示原型,但是那teacher.drink()中的drink又是哪来的呢

teacher.drink()是teacher继承Person之后,Person里面的方法,我们可以看到Teacher类中的Teacher.peototype中还有一个__proto__,点开之后这个__proto__里面就存在drink变量。

在这里插入图片描述

Teacher类继承于Person,所以其实Teacher的隐式原型Teacher.peototype的__proto__就指向于Person的显示原型Person.peototype。当drink在Teacher类找不到时,就会去Teacher的显示原型(teacher的隐式原型)中去找,要是还找不到就会去Teacher的显示原型的隐式原型中去找,层层找下去这个链就是原型链。

在这里插入图片描述

当我们访问一个对象的属性和方法时,他首先会从自身去找,如果找不到就从他的原型去找,如果还是找不到,就从他原型的原型去找,这样就形成了一个链式结构,这个结构就叫原型链

那怎么检查一个属性和方法是不是对象自身的属性和方法呢,这里面有一个方法,对象.hasOwnProperty("属性或方法名")

class Person {
    constructor(name) {
        this.name = name;
    }
    drink(){
        console.log(`我是人,我要喝水`)
    }
}
class Teacher extends Person{
    constructor(name,subject) {
        super(name);
        this.subject = subject;
    }
    teach(){
        console.log(`我是${this.name},我教${this.subject}课程`)
    }
}
const teacher = new Teacher("ldz", "js")
console.log("teacher.name",teacher.hasOwnProperty("name"))
console.log("teacher.teach",teacher.hasOwnProperty("teach"))

在这里插入图片描述

那么这个hasOwnProperty又是哪里来的呢,这个是Person继承的Object类里面的,这个里面的隐式原型就是null,也就是说如果teacher一个方法,theacher本身没有,teacher的隐式原型(teacher.__proto __ \ Teacher)没有,teacher的隐式原型的隐式原型(peototype.peototype \ Person)没有,teacher的隐式原型的隐式原型的隐式原型(Person.peototype \ Object)没有,那就真的没有了,因为teacher的隐式原型的隐式原型的隐式原型的隐式原型(Object.peototype )为null,找不下去了。

在这里插入图片描述

4:使用instanceof做类型判断

众所周知,typeof可以对数据做类型判断,但是还是有很多数据类型无法区分开来。

const object = {}
const array = []

console.log("object:\t",typeof object)
console.log("array:\t",typeof array)

上面一个对象,一个数组,但是最后函数输出如下图

在这里插入图片描述

这个时候就要用instanceof做类型判断

const object = {}
const array = []

console.log("object:\t",typeof object)
console.log("array:\t",typeof array)

const object_res = object instanceof Array;
const array_res = array instanceof Array;

console.log("object:\t",object_res)
console.log("array:\t",array_res)

在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Addam Holmes

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值