# this指向

  • 默认绑定: 非严格模式下 this 指向全局对象,严格模式下 this 会绑定为 undefined
  • 隐式绑定: 满足 XXX.fn() 格式,fn 的 this 指向 XXX。如果存在链式调用, this 永远指向最后调用它的那个对象
  • 隐式绑定丢失:起函数别名,通过别名运行;函数作为参数会造成隐式绑定丢失。
  • 显式绑定: 通过 call/apply/bind 修改 this 指向
  • new绑定: 通过 new 来调用构造函数,会生成一个新对象,并且把这个新对象绑定为调用函数的 this 。
  • 箭头函数绑定: 箭头函数没有 this ,它的 this 是通过作用域链查到外层作用域的 this ,且指向函数定义时的 this 而非执行时优先级

# 箭头函数与普通函数区别

  • 箭头函数没有this,它的this是通过作用域链查到外层作用域的this,且指向函数定义时的this而非执行时。
  • 不可以用作构造函数,不能使用new命令,否则会报错
  • 箭头函数没有arguments对象,如果要用,使用rest参数代替
  • 不可以使用yield命令,因此箭头函数不能用作Generator函数。
  • 不能用call/apply/bind修改this指向,但可以通过修改外层作用域的this来间接修改。
  • 箭头函数没有prototype属性

# let const var 区别

var

  • 存在变量提升
  • 可以重复声明
  • 在函数中使用var声明变量的时候,该变量是局部的

let

  • 不存在变量提升,let声明变量前,该变量不能使用(暂时性死区)
  • let命令所在的代码块内有效,在块级作用域内有效
  • let不允许在相同作用域中重复声明,注意是相同作用域,不同作用域有重复声明不会报错

const

  • const声明一个只读的变量,声明后,值就不能改变
  • const必须初始化
  • const并不是变量的值不能改动,而是变量指向的内存地址所保存的数据不得改动

区别

1.变量提升

  • var声明的变量存在变量提升,即变量可以在声明之前调用,值为undefined
  • let和const不存在变量提升,即它们所声明的变量一定要在声明后使用,否则报错

2.块级作用域

  • var不存在块级作用域
  • let和const存在块级作用域

3.重复声明

  • var允许重复声明变量
  • let和const在同一作用域不允许重复声明变量

4.修改声明的变量

  • var和let可以
  • const声明一个只读的常量。一旦声明,常量的值就不能改变,但对于对象和数据这种引用类型,内存地址不能修改,可以修改里面的值。

# call、apply、bind区别

  • call() 和apply()的第一个参数相同,就是指定的对象。这个对象就是该函数的执行上下文。
  • call()和apply()的区别就在于,两者之间的参数。
  • call()在第一个参数之后的 后续所有参数就是传入该函数的值。
  • apply() 只有两个参数,第一个是对象,第二个是数组,这个数组就是该函数的参数。
  • bind() 方法和前两者不同在于: bind() 方法会返回执行上下文被改变的函数而不会立即执行,而前两者是 直接执行该函数。他的参数和call()相同。

alt

# new操作符做了哪些事情

  • 1.创建了一个新对象
  • 2.把这个新对象的原型属性(proto)绑定到原函数的prototype属性(就是继承原函数原型)
  • 3.把原函数的this指向转移到这个新对象上
  • 4.返回新对象,如果这个函数没有返回其他对象的话