1. 程式人生 > >嘗試 ES6 中的箭頭函式

嘗試 ES6 中的箭頭函式

提醒:本文最後更新於 1947 天前,文中所描述的資訊可能已發生改變,請謹慎使用。

最近組裡不少同學對 ES6 很有興趣,月影老大也給大家分享過有關 ES6 的話題。接下來,我也會嘗試使用 ES6 的一些新特性並記錄下來,內容不一定全面或精確。更全面的 ES6 介紹可以參考相應標準文件,或者MDN,或者有大量高質量 ES6 譯文及原創的優秀部落格紫雲飛。另外,「奇舞週刊」近期準備開闢譯文專欄,有興趣參與的同學請聯絡我

廢話不多說,今天要介紹的是 ES6 中的箭頭函式(Arrow Function),目前只有 Firefox22+ 支援,本文示例需要在新版 Firefox 下才能正常工作。

定義

定義一個箭頭函式很簡單,基本語法是:

([param] [, param]) => {
   statements
}

param => expression

param 是引數,根據引數個數不同,分這幾種情況:

  • () => { ... } // 零個引數用 () 表示;
  • x => { ... } // 一個引數可以省略 ();
  • (x, y) => { ... } // 多引數不能省略 ();

當然,和普通函式一樣,箭頭函式也可以使用 ES6 新增的「預設引數」和「剩餘引數」( Firefox15+ 開始支援):

var func1 = (x = 1, y = 2
) => x + y; func1(); // 得到 3 var func2 = (x, ...args) => { console.log(args) }; func2(1,2,3); // 輸出 [2, 3]

箭頭函式允許多行語句或者單行表示式作為函式體。多行語句要用 {} 括起來;單行表示式不需要 {},並且會作為函式返回值:

x => { return x * x }; // 函式返回 x * x
x => x * x; // 同上一行
x => return x * x; // SyntaxError 報錯,不能省略 {}
x => { x * x }; // 合法,沒有定義返回值,返回 undefined

箭頭函式也是 JS 函式的一種,所以之前的 instanceof 和 typeof 依然可用:

var func1 = () => {};
func1 instanceof Function; // true

var func2 = () => {};
typeof func2; // "function"

特性

Nicholas C. Zakas 的部落格中指出了箭頭函式的幾個特性:不能被 new 、this 被繫結為函式定義時的 this 且無法改變、不支援 arguments 。對於最後一點,我在 Firefox24 測試發現,arguments 可以正常工作。不知道是標準有變化,還是 Firefox 的實現有偏差,我們來看前兩個特性。

箭頭函式內部沒有 constructor 方法,也沒有 prototype,所以不支援 new 操作。new (() => {}) 會觸發 TypeError 報錯。

JS 裡的 this 指標一直是新手很頭疼的事情,看一個簡單的例子:

var o = {
    x : 1,
    func : function() { console.log(this.x) },
    test : function() {
        setTimeout(function() {
            this.func();
        }, 100);
    }
};

o.test(); // TypeError : this.func is not a function

上面程式碼得不到預期結果,因為 this 發生了改變,這個問題可以這樣修正:

var o = {
    x : 1,
    func : function() { console.log(this.x) },
    test : function() {
        var _this = this;
        setTimeout(function() {
            _this.func(); 
        }, 100);
    }
};

o.test();

在函式內部使用外部事先儲存的 this 就沒問題了。也可以改用 ES5 引入的 bind 方法:

var o = {
    x : 1,
    func : function() { console.log(this.x) },
    test : function() {
        setTimeout(function() {
            this.func(); 
        }.bind(this), 100);
    }
};

o.test();

而有了箭頭函式,像下面這樣寫就可以了:

var o = {
    x : 1,
    func : function() { console.log(this.x) },
    test : function() {
        setTimeout(() => { this.func() }, 100);
    }
};

o.test();

箭頭函式的 this 始終指向函式定義時的 this,而非執行時。下面看一個嘗試改變箭頭函式 this 指標的例子:

var x = 1,
    o = {
        x : 10,
        test : () => this.x
    };

o.test(); // 1
o.test.call(o); // 依然是1

CoffeeScript

實際上,CoffeeScript 一直就支援用這種 =>(胖箭頭)定義函式;同時 CoffeeScript 還支援用 ->(瘦箭頭)定義函式。二者的區別是胖箭頭會繫結 this,瘦箭頭不會,來看一個例子,以下是 Coffee 程式碼:

this.clickHandler = -> alert "clicked"
el1.addEventListener "click", (e) => this.clickHandler(e)
el2.addEventListener "click", (e) -> this.clickHandler(e)

編譯後的 JS 程式碼是這樣的:

var _this = this;

this.clickHandler = function() {
  return alert("clicked");
};

el1.addEventListener("click", function(e) {
  return _this.clickHandler(e);
});

el2.addEventListener("click", function(e) {
  return this.clickHandler(e);
});

可以看到,使用胖箭頭的 el1 繫結的 click 函式的 this 指向函式定義時的 this;而 el2 的 click 函式的 this 指向執行時的元素本身。

JS 的箭頭函式沒看到有瘦箭頭的形式。

效能

關於箭頭函式的效能,我不想花精力去研究。一方面 ES6 標準並沒有完全確定,另一方面現在只有 Firefox 一家支援箭頭函式,對比意義不大。jsPref 上有個相關的測試,大家可以點過去看看。從已有的結果來看,箭頭函式與 bind 函式對比,效能差別不大;尤其是在 Firefox25 上,箭頭函式已經比 bind 快了。

參考:

--EOF--

提醒:本文最後更新於 1947 天前,文中所描述的資訊可能已發生改變,請謹慎使用。

相關推薦

三十四、ES6箭頭函式的使用

1、單引數箭頭函式 ES6中允許使用“箭頭”(=>)定義函式: var f = v => v; 以上程式碼相當於: var f = function( v ) { return v; } “箭頭”(=>)後面是函式體,“箭頭”(=>

es6箭頭函式 注意點

var aaabbb = 'kkkooo' setTimeout(()=>{ var aaaa = 'kkkk'; console.log(this) },1000); 因為據我瞭解,箭頭函式指向是建立時候上下文的this指向,所以天真的認為上述函式中在箭頭函式內部建立的變數

ES5,ES6箭頭函式,物件定義this的總結

最近在學ES6的時候,發現使用箭頭函式的時候的this指向不太清楚,和普通的物件建立做了一些對比,講講自己的理解,有問題希望大家和我一起討論研究 箭頭函式 和 function(){}定義的區別,箭頭函式的 這裡的所有程式碼基於chrome進行測試  這裡有幾個帖子是作為參考的

ES6箭頭函式的使用

基本用法 ES6允許使用“箭頭”(=>)定義函式。 var f = v => v; 上面的箭頭函式等同於: var f = function(v) {  return v;  }; 如果箭頭函式不需要引數或需要多個引數,就使用一個圓括號代表引數部

嘗試 ES6 箭頭函式

提醒:本文最後更新於 1947 天前,文中所描述的資訊可能已發生改變,請謹慎使用。 最近組裡不少同學對 ES6 很有興趣,月影老大也給大家分享過有關 ES6 的話題。接下來,我也會嘗試使用 ES6 的一些新特性並記錄下來,內容不一定全面或精確。更全面的 ES6 介紹可以參考相應標準文件,或者MD

javascript的一般函式ES6箭頭函式對比,以及this指向問題的深度理解

關於this的指向問題,老外有文章寫得非常棒,在看了老外的文章 並結合自己的想法再修改此篇文章 一 、基本概念 本文定義的一般函式 單純 指的是js原生函式(ES5函式) 同時ES5中的作用域只有全域

ES6函式和陣列補漏

物件的函式解構 我們在前後端分離時,後端經常返回來JSON格式的資料,前端的美好願望是直接把這個JSON格式資料當作引數,傳遞到函式內部進行處理。ES6就為我們提供了這樣的解構賦值。 let json={ a:'leiy', b:'ly' } function fun({a,b="yu"})

ES6 高階箭頭函式理解函式柯里化

前言:第一次看到多個連續箭頭函式是在一個 react 專案中,然鵝確認了下眼神,並不是對的人,因為看得一臉懵逼。em......於是開始各種搜尋,先是知道了多個連續箭頭函式就是 es6 的多次柯里化的寫法,對於函式柯里化,很久以前就知道這個名次,但是並不理解,也沒有去了解。為了弄明白多個連續箭頭函式,開始

ES6學習--箭頭函式

1. 箭頭函式基本形式 let func = (num) => num; let func = () => num; let sum = (num1,num2) => num1 + num2; [1,2,3].map(x => x * x); 2. 箭頭函式基本特點 (

阿里前端測試題--關於ES6Promise函式的理解與應用

今天做了阿里前端的筆試題目,原題目是這樣的 //實現mergePromise函式,把傳進去的陣列順序先後執行,//並且把返回的資料先後放到陣列data中const timeout = ms => new Promise((resolve, reject) => {setTimeout(() =

es6箭頭函式和es5的function函式區別

一.es6的箭頭函式 es6箭頭函式內部沒有this,使用時會上朔尋找最近的this 不可以做建構函式,不能使用new命令,因為沒有this 函式體內沒有arguments,可以使用rest引數代替

ES6箭頭函式深入理解

相對於普通函式的區別 新的書寫方式  this 的改變 不能當建構函式 沒有 prototype 屬性 沒有 arguments 物件   新的書寫方式 書寫方式很簡單!直接看下圖, 常規方式寫一個函式 const fun = function(number){

es6的(=>)箭頭函式

x => x * x 上面的箭頭函式相當於: function (x) { return x * x; } 箭頭函式相當於匿名函式,並且簡化了函式定義。 箭頭函式有兩種格式,一種像上面的,只包含一個表示式,連{ ... }和return都省略掉了。 還有一種可以包含多條語句,這時候就不能省

ES6箭頭函式的this繫結問題

關於this指向問題的討論一直是學習js不可忽視的重要部分,那些一個又一個圍繞this挖的筆試坑,彷彿永遠也填不完 var obj={ fn:function(){ console.log(this); } } obj.fn();//object  

ES6箭頭函式和普通函式有什麼區別?

1、普通函式中的this總是指向呼叫它的那個物件,    箭頭函式沒有自己的this,他的this永遠指向其定義環境,任何方法都改變不了其指向,如call()、bind()、apply()。(正是因為它沒有this,所以也就不能用作建構函式,也沒有原型物件) 2、箭頭函式不能當作建構函

es6箭頭函式return的用法

最近在專案中頻繁的使用了箭頭函式,在使用的過程中對return關鍵字用法比較困惑,下面對其使用方法進行記錄: 如果箭頭函式的程式碼塊部分多於一條語句,就要使用大括號將它們括起來,並且使用return關鍵字返回 例子: const foo = (a, b) =

解析ES6箭頭函式的this

ES6中新增了箭頭函式這種語法,箭頭函式以其簡潔性和方便獲取this的特性,接下來通過本文給大家分享ES6箭頭函式中的this,寫的十分的全面細緻,具有一定的參考價值,對此有需要的朋友可以參考學習下。如有不足之處,歡迎批評指正。 簡要介紹:箭頭函式中的this,指向與一般fun

前端專案常用es6知識總結 -- 箭頭函式及this指向、尾呼叫優化

專案開發中一些常用的es6知識,主要是為以後分享小程式開發、node+koa專案開發以及vueSSR(vue服務端渲染)做個前置鋪墊。 專案開發常用es6介紹 1、塊級作用域 let const  2、箭頭函式及this指向 3、promise、 4、as

ES6箭頭函式修復ES5this指向問題

長期以來,ES5中this物件一直的指向一個令人頭痛的問題,在物件方法中使用此,必須非常小心例如: class Animal { constructor(){ this.type = 'animal' } says(say){ setTim

ES6 箭頭函式的 this?(臨時性儲存)

是否區域性(Lexical)? 包括我在內的許多人,都會這麼描述箭頭函式裡 this 的行為:區域性的 this。什麼意思呢? <body> <div id="demo" onclick="foo()" > 點我</div&