摘要:閉包是什么這是一個在面試的過程中出現的概率為以上的問題,也是我們張口就來的問題。文章推薦我們面試中在被問到閉包這個問題是要注意的幾點閉包的延伸,讓面試變得
閉包是什么?這是一個在面試的過程中出現的概率為60%以上的問題,也是我們張口就來的問題。但是我們往往發現,在面試的過程中我們的回答并不那么讓面試官滿意,我們雖然能張口說出一些但是卻不能系統的對這個問題進行回答。面試官希望加入自己團隊的是一個基礎扎實,條理清晰,舉一反三,吃苦耐勞的人,如果我們在面試中的回答只是‘東一榔頭,西一棒槌’,結果我想已經顯而易見了。
接下來將從三個方面來說閉包:
1.閉包是什么?
2.為什么要用閉包?
3.如何使用閉包?
閉包是什么定義
閉包就是外層函數的內部函數(不過要注意它的特性)。
特性
1.它有自己的局部作用域(local scope);
2.它可以訪問外部函數的作用域(outer scope),參數(parameters),而不是參數對象;
3.它也可以訪問全局的(global scope)
4.參數和變量不會被垃圾回收機制回收(不當的使用閉包可能造成內存泄漏的原因)
閉包與作用域javascript的作用域
javascript 是一個函數級的作用域(function-level scope),而不是一個像其他語言一樣的塊級作用域(block-level-scope);此外javascript是一個異步的事件驅動語言(javascript是單線程的語言),想要了解更多的異步事件驅動我們可以看一下node.js的
閉包工作原理
1.閉包存儲外部函數變量的引用,因此總是可以訪問外部變量的更新值
2.在它的外部函數被執行并返回值后,閉包仍然可以執行(常駐內存)
為什么要用閉包例如:在for循環中我們訪問一個變化的變量時存在問題
而我們根據閉包的特性和工作原理可以很好的解決這個問題
閉包的好處
1.保存狀態(使一個變量長期駐扎在內存中)
2.避免全局變量的污染
3.允許私有成員的存在
如何使用閉包通常在函數返回時會失去對變量的訪問權限,如下面的示例:
function unClosure() { var innerVar = "I"m inner-variable"; return innerVar; } unClosure(); // returns "I"m inner-variable"
上面的示例代碼沒有多少的實際意義,我們做一下修改,如下:
function unClosure(outerVar) { return outerVar; } unClosure(); unClosure("apple"); // return "apple"; unClosure("banana"); // return "banana"; unClosure("tomato"); // return "tomato";
但是我們發現,在unClosure運行之后,我們將沒有辦法去獲得outerVar。當然,我們可以再一次運行unClosure一次又一次,但是每一次調用之后將會創造一個新的outerVar,這樣很難保證每一個outerVar是最新的,因為當前的調用沒有存儲任何引用。所以,我們可以將代碼修改如下:
function aClosure() { var longLivedVariable = "I"m here for a long time"; var innerFunction = function inner() { return longLivedVariable; } return innerFunction; } var closure = aClosure(); // 返回一個innerFunction的引用 closure(); // returns "I"m here for a long time"
我們發現aClosure沒有返回longLivedVariable,而是返回innerFunction的引用。這也即是說有一個引用一直掛載在innerFunction上,由于innerFunction上有一個longLivedVariable的引用,那么變量將一直存在。為了說明以上的推論,我們將代碼修改如下:
function aClosure(longLivedVariable) { var innerFunction = function inner() { return longLivedVariable; } return innerFunction; } var closure = aClosure("apple"); // 返回一個innerFunction的引用 closure(); // returns "apple" closure(); // returns "apple" closure(); // returns "apple" var closure2 = aClosure("banana"); // 返回一個innerFunction的引用 closure2(); // returns "banana" closure2(); // returns "banana" closure2(); // returns "banana"
當我們釣友closure(),我們一直調用的是innerFunction(),或者說是aClosure()的返回值,而對于innerFunction來說返回的是longLivedVariable.
上面的例子是保存狀態的簡單使用,下面我們來一個保存狀態和允許擁有私有成員的例子,
這個常見的就是對象。示例代碼如下:
function person(name) { return { getName: function() { return name; } } } var person = person("lisi"); person.name // returns undefined person.getName() // returns "lisi" var person2 = cat("張華"); person2.getName() // returns "張華"
這里的name即是私有成員,通過person,和person2兩個對象實例說明可以保存狀態
從上面兩個例子我們也可以看出閉包的另一個好處,通過保存狀態或將定義私有成員,可以實現避免全局變量污染的好處。
我們知道在javascript中避免全局變量污染的一般方法:
1.定義全局命名空間
2.使用一個立即執行函數
githubGist的代碼實例參考
stackflow的優秀解答
閉包與立即執行函數閉包幫我們解決了我們要全局的使用,又不想全局所帶來的污染的問題,使用閉包你可以像工廠方法一樣創建多個不同的對象。但在實際的開發過程中我們又會遇到這樣的問題,希望對象只有一份,也就是我們常說的單例模式,在javascript中函數沒法私有化,所以轉個思路我們可以讓這個工廠方法不能多次調用,而這樣的函數就是匿名函數;而且只能調用一次,就是在聲明函數的時候立即執行。
文章推薦lucy’s blog about closure
by rlynjb about closure
我們面試中在被問到閉包這個問題是要注意的幾點
閉包的延伸,讓面試變得so easy
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/90389.html
摘要:同行這么做使用實現圓形進度條前端掘金在開發微信小程序的時候,遇到圓形進度條的需求。實現也談數組去重前端掘金的數組去重是一個老生常談的話題了。百度前端技術學院自定義前端掘金一標簽概念元素表示用戶界面中項目的標題。 閑話圖片上傳 - 掘金作者:孫輝,美團金融前端團隊成員。15年畢業加入美團,相信技術,更相信技術只是大千世界里知識的一種,個人博客: https://sunyuhui.com ...
摘要:同行這么做使用實現圓形進度條前端掘金在開發微信小程序的時候,遇到圓形進度條的需求。實現也談數組去重前端掘金的數組去重是一個老生常談的話題了。百度前端技術學院自定義前端掘金一標簽概念元素表示用戶界面中項目的標題。 閑話圖片上傳 - 掘金作者:孫輝,美團金融前端團隊成員。15年畢業加入美團,相信技術,更相信技術只是大千世界里知識的一種,個人博客: https://sunyuhui.com ...
摘要:當面試中讓我解釋一下閉包時我懵逼了。這個解釋開始可能有點晦澀,讓我們抽絲剝繭摘下閉包的真面目。此文不詳述作用域有專門的主題闡述,不過作用域是理解閉包原理的基礎。這才是閉包的真正便利之處。閉包使用不當就會很坑。 原文鏈接 為什么深度學習JavaScript? JavaScript如今是最流行的編程語言之一。它運行在瀏覽器、服務器、移動設備、桌面應用,也可能包括冰箱。無需我舉其他再多不相干...
摘要:在運行腳本時,需要顯示的指定對象。大對象區每一個區域都是由一組內存頁構成的。這里是唯一擁有執行權限的內存區。換句話說,是該對象被之后所能回收到內存的總和。一旦活躍對象已被移出,則在舊的半空間中剩下的任何死亡對象被丟棄。 內存管理 本文以V8為背景 對之前的文章進行重新編輯,內容做了很多的調整,使其具有邏輯更加緊湊,內容更加全面。 1. 基礎概念 1.1 生命周期 不管什么程序語言,內存...
摘要:內部維護一個叫的局部變量,數組類型,用于存儲購買的物品清單。分析看到這題的第一反應就是用構造函數來寫。二屬性外部只能訪問不能修改這個用閉包也能解決,但是這樣記不能通過構造函數來實現了,背離了初衷,不行不過我后面還是會給出這種寫法。 背景 作為一個前端新人,免不了加各種群,和其他小伙伴們一起學習(chui bi),互相幫助(bi can)。前幾天一個小伙伴在群里發了道自己去面試的筆試題,...
閱讀 1102·2021-10-14 09:43
閱讀 1145·2021-10-11 11:07
閱讀 3112·2021-08-18 10:23
閱讀 1485·2019-08-29 16:18
閱讀 999·2019-08-28 18:21
閱讀 1474·2019-08-26 12:12
閱讀 3760·2019-08-26 10:11
閱讀 2502·2019-08-23 18:04