箭头函数与普通的函数有什么区别
1、写法不同
在 js 中,像命名式函数、函数表达式都称为普通函数。对于普通函数,需要用function关键字来声明。而箭头函数则不需要使用function关键字,在箭头前面的括号里面写参数,后面的大括号里面写方法体。箭头函数语法更加简洁清晰。
// 命名式函数
function normalFn(参数) {
// 方法体
return 'normalFn';
}
// 函数表达式
const normalFn = function(参数) {
// 方法体
return 'normalFn';
}
// 箭头函数
const arrowFn = (参数) => {
// 方法体
return 'arrowFn';
}
2、this指向不同
普通函数
在普通函数中,this 的指向是动态的,其值取决于函数是如何被调用的,通常有以下 4 种调用方式:
1)直接调用时,其指向为全局对象(严格模式下为 undefined)
function fnc() {
console.log(this); //window{}
}
fnc(); // 全局对象(global 或 window)
2)方法调用时,this指向为调用该方法的对象
let obj = {
fnc1(){
console.log('fnc1', this === obj); // fnc1 true
}
}
obj.fnc2 = function() {
console.log('fnc2', this === obj); // fnc2 true
}
function fnc3() {
console.log('fnc3', this === obj); // fnc3 true
}
obj.fnc3 = fnc3;
obj.fnc1(); // true
obj.fnc2(); // true
obj.fnc3(); // true
3)new 调用时,其指向为新创建的实例对象
function fnc() {
console.log(this); //fnc {}
}
let obj = new fnc(); // fnc 的实例 fnc {} 这里就是obj
4)call、apply、bind 调用时,其指向为三种方法的第一个参数
function fnc() {
console.log(this);
}
let obj = {name: '张三',age: 18}
fnc.call(obj) // obj对象
fnc.apply(obj) // obj对象
fnc.bind(obj)() // obj对象
bind() 函数是创建一个新的函数,不会立即执行,需要手动调用
箭头函数
箭头函数的this指向是静态的,无论如何执行或在何处执行,箭头函数内部 this 始终指向创建时所在作用域指向的对象。由于箭头函数没有自己的 this 指针,call()、apply()、bind()等方法不能改变箭头函数中this指向的。
const obj = {
fnc(arr) {
console.log(this === obj); // true(obj)
const cb = () => {
console.log(this === obj); // true(obj)
};
arr.forEach(cb);
}
};
obj.fnc([1, 2, 3]);
3、箭头函数不能作为构造函数使用
因为箭头函数没有自己的this,它的this其实是继承了外层执行环境中的this,且this指向永远不会变,并且箭头函数没有原型prototype,没法让他的实例的__proto__属性指向,所以箭头函数也就无法作为构造函数,用new调用时会报错。
var Foo = () => {};
var foo = new Foo();
new内部实现其实是分为以下四步:
1)新建一个空对象
2)链接到原型
3)绑定this,执行构造函数
4)返回新对象
function myNew() {
// 1.新建一个空对象
let obj = {}
// 2.获得构造函数
let con = arguments.__proto__.constructor
// 3.链接原型
obj.__proto__ = con.prototype
// 4.绑定this,执行构造函数
let res = con.apply(obj, arguments)
// 5.返回新对象
return typeof res === 'object' ? res : obj
}
4、箭头函数没有prototype属性。
5、参数
普通函数与箭头函数在参数上区别主要在于,箭头函数不绑定 arguments 对象。
当我们需要使用参数时,可以考虑ES6中的rest(剩余)参数。
const fn = (...args) => args[0];
fn(1,2,3,4)