ES6標準新增了一種新的函數:Arrow Function(箭頭函數)。app
箭頭函數至關於匿名函數,而且簡化了函數定義。箭頭函數有兩種格式,一種像上面的,只包含一個表達式,連{ ... }
和return
都省略掉了。還有一種能夠包含多條語句,這時候就不能省略{ ... }
和return
:函數
1 x => { 2 if (x > 0) { 3 return x * x; 4 } 5 else { 6 return - x * x; 7 } 8 }
若是參數不是一個,就須要用括號()
括起來:this
1 // 兩個參數: 2 (x, y) => x * x + y * y 3 4 // 無參數: 5 () => 3.14 6 7 // 可變參數: 8 (x, y, ...rest) => { 9 var i, sum = x + y; 10 for (i=0; i<rest.length; i++) { 11 sum += rest[i]; 12 } 13 return sum; 14 }
若是要返回一個對象,就要注意,若是是單表達式,這麼寫的話會報錯:spa
// SyntaxError: x => { foo: x }
由於和函數體的{ ... }
有語法衝突,因此要改成:rest
// ok: x => ({ foo: x })
箭頭函數看上去是匿名函數的一種簡寫,但實際上,箭頭函數和匿名函數有個明顯的區別:箭頭函數內部的this
是詞法做用域,由上下文肯定。code
回顧前面的例子,因爲JavaScript函數對this
綁定的錯誤處理,下面的例子沒法獲得預期結果:對象
1 var obj = { 2 birth: 1990, 3 getAge: function () { 4 var b = this.birth; // 1990 5 var fn = function () { 6 return new Date().getFullYear() - this.birth; // this指向window或undefined 7 }; 8 return fn(); 9 } 10 };
如今,箭頭函數徹底修復了this
的指向,this
老是指向詞法做用域,也就是外層調用者obj
:blog
1 var obj = { 2 birth: 1990, 3 getAge: function () { 4 var b = this.birth; // 1990 5 var fn = () => new Date().getFullYear() - this.birth; // this指向obj對象 6 return fn(); 7 } 8 }; 9 obj.getAge(); // 25
若是使用箭頭函數,之前的那種hack寫法:排序
var that = this;
就再也不須要了。ip
因爲this
在箭頭函數中已經按照詞法做用域綁定了,因此,用call()
或者apply()
調用箭頭函數時,沒法對this
進行綁定,即傳入的第一個參數被忽略:
1 var obj = { 2 birth: 1990, 3 getAge: function (year) { 4 var b = this.birth; // 1990 5 var fn = (y) => y - this.birth; // this.birth還是1990 6 return fn.call({birth:2000}, year); 7 } 8 }; 9 obj.getAge(2015); // 25
使用箭頭函數簡化排序時傳入的函數:
1 'use strict' 2 var arr = [10, 20, 1, 2]; 3 arr.sort((x, y) => { 4 return x-y; 5 }); 6 console.log(arr); // [1, 2, 10, 20]
var arr = [10, 20, 1, 2]; arr.sort( function(a,b){ return a-b; } ); console.log(arr); // [1, 2, 10, 20]