閉包的那些事兒
- 怎么寫一個(gè)閉包
閉包是什么就不解釋了岸啡,直接寫一個(gè)閉包函數(shù):
var f = function() {
var num = 0;
return function() {
return num += 1;
};
}
js中暇藏,函數(shù)是一等公民,定義一個(gè)函數(shù)f滨砍,它返回另一個(gè)可執(zhí)行函數(shù)function() { return num += 1; };
js中的作用域蒲每,都是一層一層向上找的纷跛,在f內(nèi)部函數(shù)里面,他的num向上找到父函數(shù)的作用域邀杏。
現(xiàn)在贫奠,我們執(zhí)行一下:
f()()
// 1
f()()
// 1
????? 感覺 不太對(duì)?為什么num沒有自增呢望蜡?唤崭?
- 內(nèi)存回收機(jī)制
為什么上面執(zhí)行結(jié)果不太對(duì),因?yàn)閳?zhí)行f()()
后脖律,f函數(shù)已經(jīng)執(zhí)行完畢了谢肾,沒有其他資源引用f,ta會(huì)被立即釋放小泉,也就是說芦疏,f()()
執(zhí)行完后,立即就釋放了微姊。
如何才不釋放呢酸茴?
// 創(chuàng)建f的引用
var fn = f();
fn()
// 1
fn()
// 2
fn()
// 3
這下就對(duì)了,num成了私有變量兢交,f擁有了私有作用域薪捍。
完了嗎?
f有了fn的引用,內(nèi)存一直得不到釋放酪穿,咋辦呢凳干?這樣的函數(shù)多了是不是會(huì)造成內(nèi)存溢出?
手動(dòng)釋放一下:
var fn = f();
fn()
// 1
fn()
// 2
fn()
// 3
// 手動(dòng)釋放f的引用
fn = null
// f的引用fn被釋放了被济,現(xiàn)在f的作用域也被釋放了救赐。num再次歸零了。
var fn = f()
fn()
// 1