惰性函數(shù)

今天啊看到一篇講js性能優(yōu)化---惰性函數(shù)的文章,之前沒(méi)聽(tīng)過(guò)這個(gè)。

主要應(yīng)用在提高js的執(zhí)行效能上,主要也是應(yīng)用在含有大量的if 判斷的地方

舉例如下:

在javascript代碼中,因?yàn)楦鳛g覽器之間的行為的差異,我們經(jīng)常會(huì)在函數(shù)中包含了大量的if語(yǔ)句,以檢查瀏覽器特性,解決不同瀏覽器的兼容問(wèn)題。例如,我們最常見(jiàn)的為dom節(jié)點(diǎn)添加事件的函數(shù):

function addEvent (type, element, fun) {
if (element.addEventListener) {
element.addEventListener(type, fun, false);
}
else if(element.attachEvent){
element.attachEvent('on' + type, fun);
}
else{
element['on' + type] = fun;
}
}

每次調(diào)用addEvent函數(shù)的時(shí)候,它都要對(duì)瀏覽器所支持的能力進(jìn)行檢查,首先檢查是否支持addEventListener方法,如果不支持,再檢查是否支持attachEvent方法,如果還不支持,就用dom 0級(jí)的方法添加事件。這個(gè)過(guò)程,在addEvent函數(shù)每次調(diào)用的時(shí)候都要走一遍,其實(shí),如果瀏覽器支持其中的一種方法,那么他就會(huì)一直支持了,就沒(méi)有必要再進(jìn)行其他分支的檢測(cè)了,也就是說(shuō),if語(yǔ)句不必每次都執(zhí)行,代碼可以運(yùn)行的更快一些。解決的方案就是稱(chēng)之為惰性載入的技巧

所謂惰性載入,就是說(shuō)函數(shù)的if分支只會(huì)執(zhí)行一次,之后調(diào)用函數(shù)時(shí),直接進(jìn)入所支持的分支代碼。有兩種實(shí)現(xiàn)惰性載入的方式,第一種事函數(shù)在第一次調(diào)用時(shí),對(duì)函數(shù)本身進(jìn)行二次處理,該函數(shù)會(huì)被覆蓋為符合分支條件的函數(shù),這樣對(duì)原函數(shù)的調(diào)用就不用再經(jīng)過(guò)執(zhí)行的分支了,我們可以用下面的方式使用惰性載入重寫(xiě)addEvent()。

function addEvent (type, element, fun) {
if (element.addEventListener) {
addEvent = function (type, element, fun) {
element.addEventListener(type, fun, false);
}
}
else if(element.attachEvent){
addEvent = function (type, element, fun) {
element.attachEvent('on' + type, fun);
}
}
else{
addEvent = function (type, element, fun) {
element['on' + type] = fun;
}
}
return addEvent(type, element, fun);
}

在這個(gè)惰性載入的addEvent()中,if語(yǔ)句的每個(gè)分支都會(huì)為addEvent變量賦值,有效覆蓋了原函數(shù)。最后一步便是調(diào)用了新賦函數(shù)。下一次調(diào)用addEvent()的時(shí)候,便會(huì)直接調(diào)用新賦值的函數(shù),這樣就不用再執(zhí)行if語(yǔ)句了

第二種實(shí)現(xiàn)惰性載入的方式是在聲明函數(shù)時(shí)就指定適當(dāng)?shù)暮瘮?shù)。這樣在第一次調(diào)用函數(shù)時(shí)就不會(huì)損失性能了,只在代碼加載時(shí)會(huì)損失一點(diǎn)性能。一下就是按照這一思路重寫(xiě)的addEvent()。

var addEvent = (function () {
if (document.addEventListener) {
return function (type, element, fun) {
element.addEventListener(type, fun, false);
}
}
else if (document.attachEvent) {
return function (type, element, fun) {
element.attachEvent('on' + type, fun);
}
}
else {
return function (type, element, fun) {
element['on' + type] = fun;
}
}
})();

這個(gè)例子中使用的技巧是創(chuàng)建一個(gè)匿名的自執(zhí)行函數(shù),通過(guò)不同的分支以確定應(yīng)該使用那個(gè)函數(shù)實(shí)現(xiàn),實(shí)際的邏輯都一樣,不一樣的地方就是使用了函數(shù)表達(dá)式(使用了var定義函數(shù))和新增了一個(gè)匿名函數(shù),另外每個(gè)分支都返回一個(gè)正確的函數(shù),并立即將其賦值給變量addEvent。

惰性載入函數(shù)的優(yōu)點(diǎn)只執(zhí)行一次if分支,避免了函數(shù)每次執(zhí)行時(shí)候都要執(zhí)行if分支和不必要的代碼,因此提升了代碼性能,至于那種方式更合適,就要看您的需求而定了。

我理解的惰性函數(shù)其實(shí)就是在函數(shù)的定義中重寫(xiě)了自身。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 背景 在開(kāi)發(fā)過(guò)程中,有時(shí)候需要對(duì)瀏覽器環(huán)境進(jìn)行檢測(cè),比如封裝一個(gè)AJAX函數(shù)的時(shí)候需要寫(xiě)一個(gè)函數(shù)進(jìn)行檢測(cè),但是常規(guī)...
    Binaryify閱讀 1,552評(píng)論 0 1
  • 惰性函數(shù)表示,此函數(shù)有很多個(gè)分支判斷,但這些分支判斷只會(huì)在第一次調(diào)用時(shí)執(zhí)行,執(zhí)行后會(huì)修改此函數(shù),再次調(diào)用時(shí)無(wú)須判斷...
    任無(wú)名F閱讀 608評(píng)論 0 0
  • Javascript的函數(shù)是運(yùn)行時(shí)定義的,可以隨時(shí)替換函數(shù)定義,非常的靈活。我們先加入一個(gè)函數(shù),用于判斷是否是ch...
    奧尼醬閱讀 1,546評(píng)論 0 1
  • 惰性函數(shù)定義: 特點(diǎn)是在第二次調(diào)用函數(shù)的時(shí)候這個(gè)函數(shù)才被正確的定義。第一次調(diào)用函數(shù)的時(shí)候只是做一些初始化的處理 特...
    蘿卜仔1閱讀 428評(píng)論 0 0
  • 惰性函數(shù)很好理解,假如同一個(gè)函數(shù)被大量范圍,并且這個(gè)函數(shù)內(nèi)部又有許多判斷來(lái)來(lái)檢測(cè)函數(shù),這樣對(duì)于一個(gè)調(diào)用會(huì)浪費(fèi)時(shí)間和...
    MakingChoice閱讀 3,465評(píng)論 1 1

友情鏈接更多精彩內(nèi)容