箭头函数为什么不能用作构造函数

箭头函数为什么不能用作构造函数

记一次面试中遇到的问题

函数分类

函数可以分为普通函数,匿名函数,箭头函数

相同点

函数的数据类型都是Function,原型链__proto__都指向Function.prototype

区别

  • 书写形式不同

     普通函数:关键字(function)函数名 (参数){}
     匿名函数:var 变量名 = 关键字(function)(参数){}
     箭头函数:(参数)=> {},参数只有一个的时候可以省略(),函数体只有一行的时候可以省略{}
    
  • 函数声明提升:

     普通函数有函数声明提升,可以在函数声明前调用函数
     匿名函数有变量提升,没有函数声明提升,要在函数声明后调用函数,调用函数时才执行函数声明
     箭头函数有变量提升,没有函数声明提升,要在函数声明后调用函数
    
  • this:

     普通函数和匿名函数有this,在全局中普通函数和匿名函数this指向window,this指向调用他的对象
     箭头函数没有自己的this,会捕获函数所在上下文的this作为自己的this,箭头函数调用call。apply时第一个参数不会影响this指向,只有传参可用
    
  • arguments:

     普通函数和匿名函数有内置对象
     箭头函数没有内置对象
    
  • 原型对象prototype:

     普通函数和匿名函数有原型对象
     箭头函数没有原型对象,也就说明了为什么箭头函数不能用作构造函数
    

构造函数的new做了哪些操作

使用构造函数new一个实例的时候,new做了哪些操作呢,
首先新建一个obj,obj的原型链指向构造函数的原型对象,改变构造函数this指向obj,如果构造函数没有return或者return的是一个常量那就返回obj作为实例,如果return了Object类型的数据,就返回return的这个Object作为实例对象
所以可以看到箭头函数没有原型对象,而且无法改变this指向所以箭头函数无法作为构造函数

  • 手动实现一个new
	function mynew(Func, ...args) {
    // 1.创建一个新对象
    const obj = {}
    // 2.新对象原型指向构造函数原型对象
    obj.__proto__ = Func.prototype
    // 3.将构建函数的this指向新对象
    let result = Func.apply(obj, args)
    // 4.根据返回值判断
    return result instanceof Object ? result : obj
}

箭头函数原型链

箭头函数有原型链:箭头函数的__proto__指向Function.prototype
Funtion.prototype.proto === Object.prototype
Object.prototype.proto === null