深入JS閉包和應用場景

看過很多的關于閉包的講解嚷硫,寫個進階總結吧膨处。

閉包在《JavaScript權威指南》定義是:函數(shù)對象本身和這個函數(shù)關聯(lián)作用域鏈的結合筹误。

想理解上面??的話就要知道在JavaScript作用域相關的有:

  • 變量作用域
    • 全局作用域
    • 本地作用域
  • 函數(shù)作用域

函數(shù)作用域可以決定變量的作用域范圍思犁。一個在函數(shù)中被定義的變量,在這個函數(shù)體中,以及該函數(shù)體中嵌套定義的所有函數(shù)內部都可見。另外和同名本地變量覆蓋全局變量同理棉磨,嵌套函數(shù)中的同名本地變量也會覆蓋其上層函數(shù)中的本地變量缤剧。

其實變量的本質就是通過對象來組織到一起的屬性集合。定義全局變量就是在全局對象(window)上定義了一個屬性

var a = {};
window.a ==== a   //true

所以對于本地變量的話缎除,相當于某個對象的屬性严就,只是沒有辦法獲取到這個對象。這個對象被稱為 調用對象 或者 聲明上下文 伴找。

引出作用域鏈

為了可以定位到具體指向哪個變量盈蛮,就需要作用域鏈。

作用域鏈:JavaScript每一個代碼塊都會與一個作用域鏈相關聯(lián)技矮,這個鏈是一個對象列表抖誉,對于每一個標識符,都依次從這個鏈的對象中查找具有相同標識符的屬性衰倦。而作用域鏈就是由全局變量和不定數(shù)量的由函數(shù)調用產(chǎn)生的調用對象構成的列表

var x = 1;
var y = 2;

// 代碼執(zhí)行到此袒炉,為了確定x和y,查詢其作用域鏈: [ window ]樊零,從 window.x 和 window.y 中取出了值
console.log( x + y );

function fnA(){
     // 函數(shù)被調用我磁,產(chǎn)生了fnA的調用對象(即為a),用于查詢變量的作用域鏈為:[ a, window ]
     var x = 2;
     // a.x 定位到x驻襟,a.y不存在夺艰,繼續(xù)從 window.y 中定位到y(tǒng)
     console.log( x + y );
}

fn();

注意函數(shù)剛定義的時候還沒有調用對象存在,所以當函數(shù)嵌套多的話沉衣,作用域鏈就很長

引出詞法作用域

詞法作用域(lexical scoping)是指郁副,函數(shù)在執(zhí)行時,使用的是它被定義時的作用域豌习,而不是這個函數(shù)被調用時的作用域存谎。

var scope = 'global scope';
function checkScope(){
     var scope = 'local scope';

     return function(){
         console.log( scope );
     }
}

var f = checkScope();
f();      // local scope

實際該函數(shù)執(zhí)行時‘fn()’時作用域中的‘scope’是 ‘global scope’ 但實際執(zhí)行使用的是定義函數(shù)時那個‘local scope‘,因為函數(shù)在執(zhí)行時使用的作用域鏈是它在定義時綁定的那個作用域鏈(準確地說是使用當時綁定的那個作用域鏈加上新建的調用對象組成的新的作用域鏈)肥隆,而不是函數(shù)調用時所處上下文的作用域鏈既荚。

最后理解閉包后,閉包的強大之處其實在于:JavaScript中的函數(shù)栋艳,通過作用域鏈和詞法作用域兩者的特性恰聘,將該函數(shù)定義時的所處的作用域中的相關函數(shù)進行了捕獲和保存,從而可以在完全不同的上下文中進行引用。

應用場景

  • 保護函數(shù)內的變量安全:如迭代器憨琳、生成器诫钓。

  • 在內存中維持變量:如果緩存數(shù)據(jù)、柯里化篙螟。

?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
  • 序言:七十年代末菌湃,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子遍略,更是在濱河造成了極大的恐慌惧所,老刑警劉巖,帶你破解...
    沈念sama閱讀 206,311評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件绪杏,死亡現(xiàn)場離奇詭異下愈,居然都是意外死亡,警方通過查閱死者的電腦和手機蕾久,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,339評論 2 382
  • 文/潘曉璐 我一進店門势似,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人僧著,你說我怎么就攤上這事履因。” “怎么了盹愚?”我有些...
    開封第一講書人閱讀 152,671評論 0 342
  • 文/不壞的土叔 我叫張陵栅迄,是天一觀的道長。 經(jīng)常有香客問我皆怕,道長毅舆,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 55,252評論 1 279
  • 正文 為了忘掉前任愈腾,我火速辦了婚禮憋活,結果婚禮上,老公的妹妹穿的比我還像新娘虱黄。我一直安慰自己余掖,他們只是感情好,可當我...
    茶點故事閱讀 64,253評論 5 371
  • 文/花漫 我一把揭開白布礁鲁。 她就那樣靜靜地躺著,像睡著了一般赁豆。 火紅的嫁衣襯著肌膚如雪仅醇。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 49,031評論 1 285
  • 那天魔种,我揣著相機與錄音析二,去河邊找鬼。 笑死,一個胖子當著我的面吹牛叶摄,可吹牛的內容都是我干的属韧。 我是一名探鬼主播,決...
    沈念sama閱讀 38,340評論 3 399
  • 文/蒼蘭香墨 我猛地睜開眼蛤吓,長吁一口氣:“原來是場噩夢啊……” “哼宵喂!你這毒婦竟也來了?” 一聲冷哼從身側響起会傲,我...
    開封第一講書人閱讀 36,973評論 0 259
  • 序言:老撾萬榮一對情侶失蹤锅棕,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后淌山,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體裸燎,經(jīng)...
    沈念sama閱讀 43,466評論 1 300
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 35,937評論 2 323
  • 正文 我和宋清朗相戀三年泼疑,在試婚紗的時候發(fā)現(xiàn)自己被綠了德绿。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 38,039評論 1 333
  • 序言:一個原本活蹦亂跳的男人離奇死亡退渗,死狀恐怖移稳,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情氓辣,我是刑警寧澤秒裕,帶...
    沈念sama閱讀 33,701評論 4 323
  • 正文 年R本政府宣布,位于F島的核電站钞啸,受9級特大地震影響几蜻,放射性物質發(fā)生泄漏。R本人自食惡果不足惜体斩,卻給世界環(huán)境...
    茶點故事閱讀 39,254評論 3 307
  • 文/蒙蒙 一梭稚、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧絮吵,春花似錦弧烤、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,259評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至伴嗡,卻和暖如春急波,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背瘪校。 一陣腳步聲響...
    開封第一講書人閱讀 31,485評論 1 262
  • 我被黑心中介騙來泰國打工澄暮, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留名段,地道東北人。 一個月前我還...
    沈念sama閱讀 45,497評論 2 354
  • 正文 我出身青樓泣懊,卻偏偏與公主長得像伸辟,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子馍刮,可洞房花燭夜當晚...
    茶點故事閱讀 42,786評論 2 345

推薦閱讀更多精彩內容

  • 我看見信夫,你在竹林里吹笛,指節(jié)上用銀色描畫著孔雀的花紋渠退;我聽見忙迁,你在竹林里吹笛,艷紅的唇吐出幽幽笛聲碎乃,聲音哀怨姊扔,又...
    南邊_20閱讀 184評論 0 1
  • 起這么個題目其實挺諷刺的恰梢,畢竟我現(xiàn)在想起寫作就全身抗拒。 但是又不得不寫梗掰,畢竟關乎飯碗的問題嵌言。萬一不小心,連自己都...
    左目情閱讀 188評論 0 0
  • 累 很累 非常累 人家一句話 你累什么累 干活干活 累 很累 非常累 人家一句話 吃的苦中苦 方為人上人 累 很累...
    先80閱讀 266評論 0 1
  • 如果能成功跨過期末大關寒假就可以專心做一個廚子了及穗! 為了讓自己專心致志體會人物有點想把企鵝先卸了摧茴,省得太浮躁。 啊...
    漣禾閱讀 444評論 1 1