哪些情况下,不能使用箭头函数?
宠辱不惊
闲看庭前花开花落
去留无意
漫随天外云卷云舒
-------------------------写下就是永恒
箭头函数使用注意事项
1. 箭头函数有什么缺点?
2. 什么时候不能使用箭头函数?
3. 箭头函数可以规避this 的问题,所有场合下都可以使用箭头函数吗?
const obj = {
name: 'syvia',
getName() {
return this.name
},
getName1: () => {
return this.name
}
}
obj.__proto__.getName2 = function() {
return this.name
}
obj.__proto__.getName3 = () => {
return this.name
}
console.log('普通函数',obj.getName())
console.log('普通函数',obj.getName2())
console.log('箭头函数',obj.getName1())
console.log('箭头函数',obj.getName3())
箭头函数有什么缺点?
1.没有 arguments
如果要用,可以用 rest 参数代替。这里我们定义一个箭头函数和一个普通函数还有一个使用 rest 参数的箭头函数:
const fn1 = () => {
console.log('arguments', arguments)
}
fn1(100, 200)
function fn2(){
console.log('arguments', arguments)
}
fn2(100, 200)
const fn3 = (...values) => {
console.log('values', values)
}
fn3(100, 200)
2.无法通过 apply、call、bind 改变this指向
这里我们在定义一个箭头函数和一个普通函数
const fn3 = () => {
console.log('this', this)
}
fn3()
function fn4(){
console.log('this', this)
}
const obj1 = {
name:'syvia',
age:18,
sex:'女',
}
fn4.call(obj1)
箭头函数的this就是他父容器的this,不是在执行的时候确定的,而是在定义的时候确定的。
我们可以发现,箭头函数的两次执行的 this 都是指向了 Windows,使用call并没有发生改变,而普通函数第一次是指向了Windows,第二次则是变成了我们传入的
什么时候不能使用箭头函数?
1.对象方法中,不适用箭头函数
const obj = {
name: 'syvia',
getName() {
return this.name
},
getName1: () => {
return this.name
}
}
我们在对象中定义了普通函数:getName和箭头函数 getName1,接下来我们来调用一下:
console.log('普通函数',obj.getName())
console.log('箭头函数',obj.getName1())
我们发现箭头函数好像并没有获取到值诶!
为什么对象方法中,箭头函数的this指向不是这个对象?
this 永远指向函数的调用者
在箭头函数中,this 指向的是定义时所在的对象,而不是使用时所在的对象。换句话说,箭头函数没有自己的 this,而是继承父作用域中的 this。
obj.getName()中this指向函数的调用者,也就是obj实例,因此this.name = “syvia”。
getName1()通过箭头函数定义,而箭头函数是没有自己的this,会继承父作用域的this。
因此obj.getName1()执行时,此时的作用域指向window,而window没有定义age属性,所有报空。
从例子可以得出:对象中定义的函数使用箭头函数是不合适的。
2.原型方法中,不适用箭头函数
const obj = {
name: 'syvia',
}
obj.__proto__.getName = function() {
return this.name
}
obj.__proto__.getName1 = () => {
return this.name
}
我们又在对象中定义了普通函数:getName和箭头函数 getName1,接下来我们来调用一下:
console.log(obj.getName())
console.log(obj.getName1())
出现问题的原因是this指向window对象,这和使用箭头函数在对象中定义方法十分类似。
3.构造函数
function Foo (name, sex) {
this.name = name
this.sex = sex
}
const Foo1 = (name, sex) => {
this.name = name
this.sex = sex
}
console.log('普通的构造函数:', new Foo('syvia', '女'))
console.log('箭头函数:', new Foo1('syvia', '女'))
构造函数是通过 new 关键字来生成对象实例,生成对象实例的过程也是通过构造函数给实例绑定 this 的过程,而箭头函数没有自己的 this。因此不能使用箭头作为构造函数,也就不能通过 new 操作符来调用箭头函数。
4.动态上下文中的回调函数
const btn1 = document.getElementById('btn1')
btn1.addEventListener('click', () => {
this.innerHTML = 'clicked'
})
如果我们在回调中不需要使用到 this,那就啥问题也没有,但是!使用到了 this,那么问题就大大的了!
箭头函数的 this 指向的是他的父作用域(这里就指向了 window),而不是指向这个button。这时候我们需要使用普通函数才可以。