箭头函数
定义
箭头函数是ES6之后增加的一种编写函数的方法,并且它比函数表达式要更加简洁
- 箭头函数不会绑定this、arguments属性;
- 箭头函数不能作为构造函数来使用(不能和new一起来使用,会抛出错误);–> (因为箭头函数没有原型);
和普通函数对比
普通函数
1 2 3 4 5 6 7 8
| function foo1() { };
const foo2 = function (name, age) { console.log("函数体代码"); console.log(name, age); };
|
箭头函数
1 2 3 4 5
| const foo3 = (name, age) => { console.log("箭头函数函数体代码"); console.log(name, age); }
|
箭头函数简写
- 如果箭头函数只有一个参数,那么()可以省略
1 2 3 4 5 6 7 8 9 10
| const names =["fsllala","fsl","forward"]; const nums =[20,30,45,66,73];
names.forEach(item=>{ console.log(item); })
const newNums = nums.filter(item=>{ return item%2==0; })
|
- 如果箭头函数只有一行执行代码,那么{}可以省略
1 2 3 4 5 6 7
| const names = ["fsllala", "fsl", "forward"]; const nums = [20, 30, 45, 66, 73];
names.forEach(item => console.log(item))
const newNums = nums.filter(item => item % 2 == 0)
|
- 只有一行执行代码,这行代码的表达式结果会作为函数的返回值默认返回
1 2 3 4 5 6 7 8 9 10 11
| const nums = [20, 30, 45, 66, 73]; const newNums = nums.filter(item => item % 2 == 0); console.log("newNums",newNums);
const arrFn1 =()=>{ return 123; }
const arrFn = ()=>123; console.log(arrFn());
|
- 如果默认返回值是一个对象,那么这个对象必须加()
- 我们先看如下现象,不难发现,当函数的返回值是对象形式的时候,不能区分
{}
到底是执行体,还是返回的对象;
1 2 3 4 5
| const arrFn1 = () => 123; const arrFn2 = () => "fsllala"; const arrFn3 = () => [2, 3, 4, 5, 1]; const arrFn4 = () => { name: "fsllala" }; const arrFn5 = ()=>{}
|
- 为了区分,这个对象必须加();代表箭头函数的默认返回值是个对象;
1
| const arrFn4 = () => ({ name: "fsllala" });
|
箭头函数this指向
箭头函数不使用this的四种标准规则(也就是不绑定this);箭头函数内部没有绑定自己的this,而是根据外层作用域来决定this;
所以箭头函数中的this和普通变量的查找机制一样,当前作用域没有,会向上层作用域查找;
普通函数没有这个this查找机制,而是遵循this的四种标准规则;详见:this
- 全局环境this
1 2
| console.log("window", this);
|
- 隐式绑定
绑定改的是函数内部的this指向,但是箭头函数内部没有this,会向上层作用域查找this,但并没有改变上层作用域中的this指向
1 2 3 4 5 6 7 8 9
| const foo = () => { console.log(this); } const obj = { name: "fsllala", say: foo }
obj.say();
|
- 显示绑定
绑定改的是函数内部的this指向,但是箭头函数内部没有this,会向上层作用域查找this,但并没有改变上层作用域中的this指向
1 2 3 4 5
| const foo = () => { console.log(this); } foo(); foo.call("aaa");
|
- 箭头函数 例一:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29
| const obj = { name: "fsllala", say: function () { const bar = () => { console.log("bar", this); } return bar } }
const fn = obj.say(); fn();
|
- 箭头函数 例二:
obj是个对象,是没有自己的作用域的;可能有人会说obj是用const声明的,但其实块级作用域形式为{ const xxx=xxxx;}
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29
| const obj = { name: "fsllala", say: () => { const bar = () => { console.log("bar", this); } return bar } }
const fn = obj.say(); fn();
|
- 箭头函数 例三:
模拟回调函数的实现
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| function request(url, callbackFn) { const arrs = ["fsl", "fsllala", 'forward']; callbackFn(arrs); }
const obj = { names: [], network: function () { request("/namesArr", function (params) { console.log(params); }) } }
obj.network();
|
需求:将回调函数返回的数据添加到obj.names中;
- methods1:const that = this;
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28
| function request(url, callbackFn) { const arrs = ["fsl", "fsllala", 'forward']; callbackFn(arrs); }
const obj = { names: [], network: function () { const that = this; request("/namesArr", function (params) { console.log(this); that.names = [...params]; }) } }
obj.network(); console.log(obj);
|
实际操作的位置(业务)中讲普通函数改为了箭头函数;
1 2 3 4 5 6 7 8 9 10 11
| const obj = { names: [], network: function () { request("/namesArr", (params) => { console.log(this); this.names = [...params]; }) } }
|
整体代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
| function request(url, callbackFn) { const arrs = ["fsl", "fsllala", 'forward']; callbackFn(arrs); }
const obj = { names: [], network: function () { request("/namesArr", (params) => { console.log(this); this.names = [...params]; }) } }
obj.network(); console.log(obj);
|