2017-05-04 127 views
-1

我正在學習JavaScript的過程。雖然我完全理解JavaScript只有函數作用域而不是作用域作用域,但我偶然發現了一個完整創建函數的for循環的例子,我完全忽略了爲什麼下面的例子不能像預期的那樣工作。Javascript關閉內部for循環

var funcs = []; 
 
for (var i = 0; i < 3; i++) {  // let's create 3 functions 
 
    funcs[i] = function() {   // and store them in funcs 
 
    console.log("My value: " + i); // each should log its value. 
 
    }; 
 
} 
 
for (var j = 0; j < 3; j++) { 
 
    funcs[j]();      // and now let's run each one to see 
 
}

它輸出這樣的:

我值:3
我值:3
我值:3

而不是:

我的價值:0
我的價值:1
我值:2

現在我知道了解決辦法是這樣的事情是創建一個返回函數返回一個函數我的價值,這將創建一個封閉的功能。

但是,我的問題是,我已經看到了一些我不太明白的解釋,爲什麼這個例子不起作用,究竟發生了什麼?

我不確定陣列func被如何填充有三個鍵:

FUNC [0],FUNC [1]和FUNC [2],而函數聲明將總是返回3?爲什麼func [0]甚至會首先存在,而不僅僅是func [3]?在我看來,在for循環中創建了某種範圍,但僅用於分配鍵,但不適用於我覺得奇怪的分配。

有人能教導我嗎?如何逐步評估for循環的外觀和原因?

非常感謝您的幫助!

+0

函數中'i'的值是引用外面的'i'的值,它不斷變化。所以,當你最後所有的'func [x]'時,'i'的值是3(它打破了'i <3'處的'for'循環),這向你顯示。 –

+2

另請注意,在ES2015中,通過'let'和'const'聲明JavaScript *確實具有塊範圍。 – Pointy

+0

*雖然我完全理解JavaScript只有函數作用域而不能阻止作用域*你完全理解不正確。 – 2017-05-04 16:29:03

回答

-1

func [0],func [1]和func [2]而函數聲明總是返回2?

func[i]總是返回3,因爲i3功能運行時。

在我看來,有某種範圍在創建for循環

沒有(當然,有,但let是不是在玩,所以它不是用於任何事物)。範圍由封閉函數定義。 i存在於範圍內並被for循環改變。


將如何一步步for循環的樣子,爲什麼步驟評價?

var funcs = []; 

創建一個數組

for (var i = 0; i < 3; i++) {  // let's create 3 functions 

組I爲0,1,2,3

funcs[i] = function() {   // and store them in funcs 
    console.log("My value: " + i); // each should log its value. 
    }; 

在任何i分配的功能到該陣列是目前

} 

結束循環的

for (var j = 0; j < 3; j++) { 

設置j爲0,1,2,3

i是仍然3.

funcs[j]();      // and now let's run each one to see 

調用第一功能。 i3。 調用第二個函數。 i3。 調用第三個函數。 i3

} 

Fin。

+0

雖然這也有點混淆,因爲這意味着JavaScript將我作爲參考傳遞給我,對嗎?我認爲JavaScript在所有情況下都是按值進行調用的,但是數組和對象呢? – Sebastian

+0

@Sebastian - 它不會傳遞任何變量。當你調用一個函數時,你的代碼永遠不會傳遞任何參數。 – Quentin