亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

閉包可以讓這些變量的值始終保持在內存中,那為什么這樣輸出后還是原來的值

閉包可以讓這些變量的值始終保持在內存中,那為什么這樣輸出后還是原來的值

白豬掌柜的 2019-02-25 12:58:50
function f1(){    var n =9;    nAdd=function(){        n=n+1;    }    function f2(){       console.log(n);    }    return f2;} var result=f1(); result(); //9 nAdd(); result();// 10 var consult=f1(); consult();//9如圖代碼所示,正在學習閉包,阮老師提到閉包作用之一就是可以讓這些變量的值始終保存在內存中,1.那為什么consult()這里打印出來的不是10,而是9呢?n值不是被保存下來了嗎?2.還有就是“f2被賦給了一個全局變量,這導致f2始終在內存中,而f2的存在依賴于f1,因此f1也始終在內存中” 這句話又是什么意思呢?f2為什么被賦給了一個全局變量?這個變量是誰?
查看完整描述

2 回答

?
寶慕林4294392

TA貢獻2021條經驗 獲得超8個贊

1.每次運行f1,函數體都會重新執行,所以在第二次運行f1后,nAdd函數體中的n已經變成了新的n,值為9

2.全局變量是resultconsult。這句話的f2f1指的是運行上下文,具體到這個問題可以理解為變量nf2


查看完整回答
反對 回復 2019-03-06
?
回首憶惘然

TA貢獻1847條經驗 獲得超11個贊

閉包講清楚不是很容易,我盡量講得清楚些

1.那為什么consult()這里打印出來的不是10,而是9呢?n值不是被保存下來了嗎?
這個問題可以簡化下,實際就是下面這個問題:
var result=f1(); // 內存里保存了一個 nvar consult=f1(); // 內存里也保存了一個 n

問題是,但是這兩個 n 是同一個么?

如果是同一個,那就是題主的意思;
不是同一個,就是阮老師的意思;

實際上不是同一個,js權威指南上是這么說的

https://img1.sycdn.imooc.com//5c7f558d0001b2c705380074.jpg

我的理解就是,這個 n 是函數調用的時候才添加到作用域鏈的,那么兩次調用函數賦值給變量,當然聲明了兩次,添加了兩次,而且在不同的作用域鏈中,如果是同一個 n 在同一個作用域,不就是重復聲明了么?你把 var 換成 let 會報錯的,為什么說在不同的作用域鏈中呢?當你聲明了 consult 之后,consult的作用域鏈中全局對象里有 result,result的作用域鏈中全局對象里有 consult 嘛?明顯沒有啊,所以兩個 n 在不同的作用域鏈中,當然不是同一個;或者再粗淺理解下,你調用一個函數兩次賦值給不同變量,難道函數內的變量都是為兩個變量共享,用的是同一個嘛?當然不是啊,,,

2.還有就是“f2被賦給了一個全局變量,這導致f2始終在內存中,而f2的存在依賴于f1,因此f1也始終在內存中” f2為什么被賦給了一個全局變量?這個變量是誰?

var result=f1(); // f1() 函數執行到 return f2,就把 f2 賦值給了 result,result 是全局變量

var consult=f1(); // f1() 函數執行到 return f2,就把 f2 賦值給了 consult,consult 是全局變量

2.還有就是“f2被賦給了一個全局變量,這導致f2始終在內存中,而f2的存在依賴于f1,因此f1也始終在內存中” 這句話又是什么意思呢?

var result=f1();//result=f2 不完全等價,但是可以用來參考

因為把 f2 賦值給 result,實際上就是在 result 上保存了對 f2的引用,而 f2 里又保存了對 n 的引用,而 f2 和 n 都存在于 f1 的局部環境里,所以導致了 n,f2,f1 都不會被垃圾回收,也就是說 f2,f1,n 都保存在內存中;(因為 js 的垃圾回收機制存在引用計數的規則,當這個值的引用次數變成 0 時,這個值才會被垃圾回收,釋放內存,引用次數不為 0 ,就繼續保存在內存中,不會被垃圾回收)

(實際上我覺得 f1 已經不在內存中了,不過這個不影響閉包的理解)


查看完整回答
反對 回復 2019-03-06
  • 2 回答
  • 0 關注
  • 1585 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號