js设计模式-构造函数模式(创建型)

111 阅读3分钟

一、什么是构造函数

一个函数,如果是被用来实例化对象的,那么就称之为构造函数

二、实例化&实例化的几种方式

实例化:创建一个对象的过程就叫实例化

实例化的方式:

    const piaopiao = new Object({ name: 'piaopiao', age: 20 })

    console.log('piaopiao', piaopiao)

image.png

通常我们不会使用new Object来创建对象,一般都是这样写的 const piaopiao = { name: 'piaopiao', age: 20 },但是你要知道这其实是new Object({ name: 'piaopiao', age: 20 })的语法糖

此外,还可以进行new Arraynew Stringnew Number

Object Array String Number这些,是js这门语言内置的构造函数,js同时也支持自定义构造函数,就像这样:

    function Girl(name, age) {
      Object.assign(this, { name, age })
    }


    const piaopiao = new Girl('飘飘', 20)
    console.log('piaopiao', piaopiao)

image.png

在这个例子中,你应该注意到了,函数的首字母是大写的

三、new操作符干了啥

  1. 开辟一块空间,用来存放实例对象
  2. 将this指向实例
  3. 将构造函数中的属性和方法绑到实例对象(this)上
  4. 构造函数的prototype属性赋值给实例的__proto__属性,它俩完全相等
  5. return this

四、构造函数的返回值

  1. 函数默认return undefined,而构造函数默认return this,return this通常不需要写,但是你要清楚,这是new操作符默认给构造函数添加了return this
    function Girl(name, age) {
      Object.assign(this, { name, age })
      return this
    }
  1. 如果return了一个简单数据类型,比如return 100,那么这句代码会被忽略

  2. 如果return了一个复杂数据类型,比如return [],那么即使使用new,得到的结果也会是[]

    function Girl(name, age) {
      Object.assign(this, { name, age })
      return []
    }

五、一些附带的知识点介绍

new.target

new.target是用来检测函数有没有被new调用

    function Girl(name, age) {
      Object.assign(this, { name, age })
      if (new.target) {
        console.log(new.target)
      } else {
        throw '普通调用'
      }
    }


    Girl('飘飘', 20) // throw '普通调用'
    new Girl('飘飘', 20) // Girl函数

instanceof

instanceof通常我们用来判断一个实例是否是由某个构造函数实例化而来,举个栗子:

    function Girl(name, age) {
      Object.assign(this, { name, age })
    }

    const girl = Girl('飘飘', 20)
    const girl1 = new Girl('飘飘', 20)

那么很明显,girl instanceof Girl会返回false,girl1 instanceof Girl会返回true

girl1 instanceof Object也是返回true的,所以instanceof是检测构造函数的property属性是否存在于某个实例的原型链上,这样描述比较完整

综上,由于girl1 instanceof Girl为true,所以girl1可以使用构造函数Girl上的属性和方法;由于girl1 instanceof Girl为true,所以girl1可以使用构造函数Object上的属性和方法

hasOwnProperty VS in

hasOwnProperty判断一个属性是否是实例的私有属性

in判断一个属性是否是实例的属性,包括原型上的属性

image.png

hasOwnProperty可以使用Object.hasOwn代替:juejin.cn/post/714983…

六、prototype

函数都有prototype属性,它就是函数的原型对象,当这个函数是通过new调用的时候,实例的__proto__就是函数的prototype属性

image.png

原型链就是沿着__proto__向上查找,直到找到Object.prototype,它的__proto__值为null,所以原型链的顶端是null

image.png