Skip to content
On this page

image.png

es5 类与继承

// 父类
class Person {
    construtor(name, age){
        this.name = name
        this.age = age
    }
    sayHello(){
        console.log("父类")
    }
}

// 子类,会继承父类的变量与方法;construtor 中必须传入父类有的变量,并执行 super
class Student extends Person {
     construtor(name, age, sex){
        super()
        this.sex = sex
    }
    learn(){
         console.log("子类")
    }
}

const zhangsan = new Student('张三',16,'男')
zhangsan.sayHello() // 父类
zhangsan.learn() // 子类

继承

  • 子类,会继承父类的变量与方法;
  • construtor 中必须传入父类有的变量,并执行 super()

instanceof

判断两个对象是否在同一条原型链上

zhangsan instanceof Student // true
zhangsan instanceof Person // true
zhangsan instanceof Object // true
zhangsan instanceof Array // false

原型

把上面的类例子改成原始的写法,可以参考上一个学习篇章大师课中实战栏目的内容

function Student(name,age){
    this.name = name
    this.age = age
}
Student.prototype.learn = function(){
    console.log("子类")
}

const zhangsan = new Student('张三',18)
console.log(zhangsan)
  • 打印 zhangsan 对象

image.png

  • 打印 zhangsan.__proto__

image.png

  • 打印 Student.prototype

image.png

zhangsan.__proto__Student.prototype 的打印是一样的,为什么呢?

  • 我们在一个类或者 function 下定义方法就是使用 Student.prototype.learn 的形式

  • 创建实例,即 new 的时候到底做了什么

    • 首先创建一个新的空对象
    • 然后将空对象的 __proto__ 指向构造函数的原型即 :obj.__proto__ = Student.prototype
    • 将 this 指向这个空对象并执行构造函数,apply
    • 构造函数有返回值则返回返回值,否则返回这个空对象
    // 代码实现
    function myNew(Con, ...args) {
        // 创建一个新的空对象
        let obj = {};
    
        // 将这个空对象的__proto__指向构造函数的原型,即 obj.__proto__ = Con.prototype;
        Object.setPrototypeOf(obj, Con.prototype);
    
        // 将this指向空对象
        let res = Con.apply(obj, args);
    
        // 对构造函数返回值做判断,然后返回对应的值
        return res instanceof Object ? res : obj;
    }
    
  • 为什么 obj.__proto__ = Student.prototype,因为 new 做了这件事情,并且我们在 类/function 中定义中就是这样去声明一个方法的

仔细看前面的打印

Function 是所有函数的构造函数,图解:

image.png

image.png

image.png