姜小白問:“分時函數是幹什麼用的?”
“同樣也是為了讓JS的性能更加的出色,避免在短時間調用大量數據的時候產生的卡頓感!說白了一起都是為了用戶體驗!畢竟體驗為王嘛!”,麥克回答道
姜小白又問:“舉個真實案例OK嗎?”
“這個在網上有很多,比如手機版的今日頭條,我們在刷新聞或者視頻的時候,只要產生滾動就會加載數據沒錯吧?”
“是的。”小白點點頭。
“那麼如果一次加載10條數據沒有問題,但一次加載2000條數據會怎麼樣?” 麥克問
“那肯定會變的很卡,或者一直在loading吧”
“正解”
閒言少敘,直接看代碼見真章
分數函數(throttle)的實現
先看下沒有經過優化的代碼:
那麼這2000多次的循環瞬間就完成了,當然這樣的計算量還是沒什麼問題的,但如果我們是調用服務器端的數據恐怕就沒這麼樂觀了。
接下來我們先了解下分時函數的實現邏輯,代碼不是重點,重點是解決問題的思路和想法。
假設,我們要生產2000個機器人,有兩個生產方案。
方案一:一個小時全部生產出來連軸轉,全部生產完成後交付客戶,毫無疑問這將會讓客戶等待一個小時。
方案二:將這兩2000個機器人分組,可以是10個一組也可以是20個一組,然後按組進行生產,比如20分鐘生產一組,完成一組後馬上交付客戶,接著生產下一組。那麼客戶20分鐘就能得到一組機器人,感受是不是會好很多呢?
我們的分時函數就是方案二。
分時函數代碼如下:
小白說:“這個函數的思路我是理解的,只是其中有一句不是特別明白”
Math.min(count || 1, arr.length)
首先 Math.min是求最小值,語法格式如下:
Math.min(x,y)
然後是 JavaScript中的||(或運算符)
只要有一個條件為true時,結果就為true;
當兩個條件都為false時,結果才為false;
當一個條件為true時,後面的條件不再判斷
count || 1, arr.length的作用就是當arr.length的數值小於 count 的時候獲取arr.length
舉個例子:
Math.min(8 || 1, 7)
這裡會先進行括號內的或運算 8 || 1結果還是8,那麼就變成了
Math.min(8 , 7)
很顯然,最小值是7.
可複製代碼:
var timeChunk = function (arr, fn, count) {
var obj, t;
var start = function () {
for (var i = 0; i < Math.min(count || 1, arr.length); i++) {
var obj = arr.shift();
fn(obj)
}
};
return function () {
t = setInterval(function () {
if (arr.length === 0) {
return clearInterval(t);
}
start()
}, 200)
}
}
var ary = [];
for (var i = 1; i <= 2000; i++) {
ary.push(i);
};
var renderFriendList = timeChunk(ary, function (n) {
var div = document.createElement('div');
div.innerHTML = n;
document.body.appendChild(div);
}, 10);
renderFriendList();
總結:
分時函數將大的數據進行分階段加載,避免在獲取大量數據或者計算時的卡頓現象,起到了性能優化的作用,提高了用戶體驗。
閱讀更多 前端講書人麥克黑 的文章
關鍵字: 函數 機器人 JavaScript