构造函数、原型与原型链| 青训营笔记

86 阅读2分钟

这是我参与「第五届青训营 」伴学笔记创作活动的第 9 天

前言

在js中,对象的底层实现采用了构造函数的形式。并且在对象的继承方面与其他语言有着巨大的差异,这就涉及到js独有的特性,原型链,从原型链中我们能够了解对象之间的关系。

构造函数

js中的函数本质是个对象, 可以通过与new关键字配合构造实例对象

//构造函数名首字母一般大写与普通函数区分
function Star(name, age) {
    this.name = name
    this.age = age
}

const ldh = new Star('kun', 2.5)

console.log(ldh)

输出结果

Star {name: 'kun', age: 2.5}

构造函数是在js还未推出class前构建类的解决方案

原型prototype

在js中,每个引用类型(对象、数组、函数)都存在其原型

函数在定义时会自动添加prototype属性

对象和数组在定义时会自动添加__proto__属性

function Star(name, age) {
    this.name = name
    this.age = age
}

const ldh = new Star('kun', 2.5)
const Star_prototype = Star.prototype
const ldh_prototype = ldh.__proto__

console.log(Star_prototype)
console.log(Star_prototype === ldh_prototype)

输出结果

{constructor: ƒ Star(name, age)}
true

可以得出通过构造函数得到的实例对象,其原型对象即为构造函数原型对象

并且可以发现原型对象上存在constructor属性,能够得到其构造函数

原型prototype的作用

多个实例对象中共用的属性或方法挂载在其原型对象上,避免了内存浪费,调用方法时若实例对象上不存在该属性或方法,则会顺其原型链向上查找直至找到或到达原型链尽头

function Star(name, age) {
    this.name = name
    this.age = age
    this.sing = function() {
        that = this
        console.log('及你太美')
    }
}

Star.prototype.jump = function() {
    console.log('跳')
}

const kun1 = new Star('kun', 2.5)
const kun2 = new Star('kun', 2.5)

console.log(kun1.sing == kun2.sing)
console.log(kun1.jump == kun2.jump)

输出结果

false //sing方法未共用,浪费内存
true //jump方法共用

原型链

prototype.png

原型与原型间形成了类似链表的结构,并且实例对象和构造函数有参与,基本关系如下

ldh.proto->Star.prototype->Object.prototype->null

原型对象也与其构造函数和实例对象形成一个环状结构

const obj = new Object({})

console.log(obj.__proto__ == Object.prototype)

输出结果

true

Object实例对象也与Object构造函数、Object原型对象构成环状结构,并且学会了构建对象的新操作