封裝Car對象
var car=(function(){
var speed=0;
function set(s){
speed = s
}
function get(){
return speed
}
function speedUp(){
speed++
}
function speedDown(){
speed--
}
return {
set:set,
get : get,
speedUp:speedUp,
speedDown:speedDown
}
})()
car.set(30) //是對象的用法,返回的應(yīng)該是對象懊纳,對象的返回值需要用函數(shù)
car.get()
car.speedUp()
car.speedDown()
car.get()
效果如圖:不能直接對speed進(jìn)行操作,封裝在一個包里亡容,用函數(shù)去操作這個變量嗤疯,這個變量就是局部變量了,car是全局變量闺兢,得不到釋放茂缚,所以返回的對象得不到釋放,所以對象應(yīng)用的方法得不到釋放,方法得不到釋放脚囊,speed得不到釋放龟糕,生成閉包。
如何連續(xù)輸出0悔耘,1讲岁,2,3衬以,4
原代碼:
for(var i=0;i<5;i++){
setTimeout(function(){
console.log('delayer:'+i)
},0)
}
//"delayer:5"
"delayer:5"
"delayer:5"
"delayer:5"
"delayer:5"
setTimeout會把當(dāng)前執(zhí)行的加到任務(wù)隊列里缓艳,for循環(huán)相當(dāng)于設(shè)置了5個定時器,這時候i=5看峻,再去執(zhí)行郎任。再說一次,for循環(huán)對于閉包备籽,干擾更大,所以分井,實質(zhì)上的影響不僅僅在于循環(huán)幾次车猬,最后要決定執(zhí)行幾次,還有這個i的值的影響尺锚。前面的閉包珠闰,盡量讓i的賦值在函數(shù)內(nèi)部的作用域,所以造了個閉包瘫辩,并立即執(zhí)行伏嗜,i不需要引用for循環(huán)得到的i值。
如何利用呢伐厌?
for(var i=0;i<5;i++){
(function(j){
setTimeout(function(){
console.log('delayer:'+j)
},0)
})(i)
}
//"delayer:0" 又是立即執(zhí)行的函數(shù)承绸,這次i的賦值遵從for循環(huán)的取值,這是什么情況呢挣轨?
//就是循環(huán)時先把函數(shù)的變量i賦值军熏,但是延時執(zhí)行,for循環(huán)依然正常循環(huán)卷扮,雖然函數(shù)執(zhí)行時荡澎,i已經(jīng)是5了。
"delayer:1"
"delayer:2"
"delayer:3"
"delayer:4"
for(var i=0;i<5;i++){
(function(j){
setTimeout(function(){
console.log('delayer:'+j)
},10000 - 1000*j)
})(i)
}
//"delayer:4"
"delayer:3"
"delayer:2"
"delayer:1"
"delayer:0"
這里只是把定時器的順序換了下晤锹,數(shù)字越大摩幔,延時越短,越靠前執(zhí)行嘛鞭铆。
for(var i=0;i<5;i++){
setTimeout(function(j){
return function(){
console.log('delayer:'+j)
}
}(i),0)
}
//"delayer:0"
"delayer:1"
"delayer:2"
"delayer:3"
"delayer:4"
定時器里的函數(shù)會立刻執(zhí)行或衡,跟上面的那個延時的不一樣,上面的函數(shù)里有定時器啊,這個輸出是立刻的薇宠。
執(zhí)行過程中傳遞i偷办,然后里面return的那個結(jié)果就是一個函數(shù),setTimeout就能用這個函數(shù)澄港,用的過程中椒涯,用到了j,中間加個臨時變量存進(jìn)去了,用到的時候回梧,就從上一級去找废岂,每當(dāng)i賦值了,j=arguments[0]也擁有了值狱意。
var makeCounter=function(){
var count = 0
return function(){
return count++
}
}
var counter = makeCounter()
var counter2=makeCounter()
console.log(counter()) //0
console.log(counter())//1
console.log(counter2())//0
console.log(counter2())//1
這里的意思湖苞,聲明不一樣的兩個變量同時指向一個函數(shù),通過作用后详囤,兩者得到了兩個獨立的作用域?qū)ο蟛乒牵ハ嗖挥绊懙摹:瘮?shù)只是一種操作方法藏姐。