国产xxxx99真实实拍_久久不雅视频_高清韩国a级特黄毛片_嗯老师别我我受不了了小说

資訊專欄INFORMATION COLUMN

關(guān)于 setTimeout 與 setInterval,你需要知道的一切

rottengeek / 596人閱讀

摘要:這里是結(jié)論,將是更驚艷的那一個(gè)。瀏覽器隔一段時(shí)間像服務(wù)器發(fā)送一個(gè)請求,詢問這里有沒有需要更新的消息。在響應(yīng)回來時(shí),才會繼續(xù)發(fā)出第二個(gè)請求。但是,顯然的,這對我們要做的事來說并不算是什么問題。

我們都知道的是setTimout是用來延遲一個(gè)簡單的動作的,然而,setInterval的目的是用來重復(fù)執(zhí)行某個(gè)動作的。

然后,以上只是一半的事實(shí)。因?yàn)槿绻粋€(gè)函數(shù)需要在一個(gè)間隔時(shí)間內(nèi)重復(fù)的執(zhí)行,你也可以輕松的使用 setTimeout 設(shè)定延遲時(shí)間,被延遲執(zhí)行的函數(shù)再進(jìn)行自調(diào)用以此實(shí)現(xiàn)循環(huán)。

所以,這里有2種方法做同樣的事

一個(gè)用setInterval

var doStuff = function () {
  // Do stuff
};
setInterval(doStuff, 1000);

一個(gè)用setTimeout

var doStuff = function () {
    // DoStuff
    setTimeout(doStuff, 1000); 
};
setTimeout(doStuff, 1000);
// 如果你想立即執(zhí)行函數(shù),可以這樣寫
var doStuff = function () {
    setTimeout(doStuff, 1000);
}
doStuff();
// 或者,更酷的方式,使用立即執(zhí)行函數(shù)
(function doStuff () {
   // Do Stuff
   setTimeout(doStuff, 1000);
}())

這必然導(dǎo)致下面兩個(gè)問題

問題:setInterval和self-invoking setTimeout-loops是可以互相替換的嗎?
答案:不,當(dāng)然不行。它們之間有著很細(xì)微的區(qū)別,但是如果想寫出好的代碼,這些細(xì)微的區(qū)別便是你想知道的事。

當(dāng)然,接下我將會訴說的,第一,我將告訴你,我們通常會遇到什么樣的問題,第二,我將開始介紹它們之間細(xì)微的區(qū)別,這些區(qū)別將讓我們從這兩個(gè)選擇中選出更具吸引力的那個(gè)一,第三,我將告訴你其實(shí)根本不用關(guān)心另一個(gè)。然后。這里是結(jié)論,setTimeout將是更驚艷的那一個(gè)。接下來我將一點(diǎn)一點(diǎn)解釋。

進(jìn)程堵塞

首先:如果你試著重復(fù)調(diào)用的函數(shù)并不會化太多的時(shí)間來跑,那么將不會有任何問題。即使如此,被調(diào)用的函數(shù)依然會出現(xiàn)2中不同的情況:它既可以在CPU上高集中的運(yùn)行腳本,或者它也可以在腳本流外先發(fā)出一個(gè)命令,并等待結(jié)果的到來。

我們主要研究先看第二種情況。典型的便是ajax回調(diào):你的腳本并不會等待服務(wù)器的響應(yīng),它會自己執(zhí)行到最后,并讓回調(diào)函數(shù)來監(jiān)聽ajax響應(yīng)。

現(xiàn)在,一些網(wǎng)站想要你保持實(shí)時(shí)更新,像Gmail,當(dāng)你獲得一封新的郵件時(shí)便會刷新你的郵箱。這里服務(wù)端有新消息時(shí)便實(shí)時(shí)通知瀏覽器端的技術(shù),通常叫做ajax輪詢。瀏覽器隔一段時(shí)間像服務(wù)器發(fā)送一個(gè)請求,詢問這里有沒有需要更新的消息。

你也許會想,你很擅長使用setInterval

// 不要這樣做
var pollServerForNewMail = function () {
  $.getJSON("/poll_newmail.php", function (response) {
    if (response.newMail) {
      alert(
        "New mail. At last. You made me walk all the way to the server and back every " +
        "second for this, so if this isn"t life-or-death, you got another thing coming."
      );
    }
  });
};
setInterval(pollServerForNewMail, 1000);

其實(shí)像上面那樣寫并不好。因?yàn)檎埱蟀l(fā)送出去到回來是需要時(shí)間的,但是這段時(shí)間誰能保證會比你設(shè)置的間隔時(shí)間要短呢?

一個(gè)典型的初學(xué)者的錯(cuò)誤,會想將輪詢的間隔時(shí)間設(shè)置的長一點(diǎn)也許可以解決這個(gè)問題。然后,事實(shí)是,無論你的間隔時(shí)間設(shè)的是多少,它依然有可能比,ajax響應(yīng)的時(shí)間短。也就是說,有可能會發(fā)生,第一個(gè)請求還沒回來的情況下,第二請求又已經(jīng)發(fā)出去了。而你需要的是兩個(gè)請求之間有呼吸的空間,而setTimeout便可以解決這個(gè)問題。

(function pollServerForNewMail() {
  $.getJSON("/poll_newmail.php", function (response) {
    if (response.newMail) {
      alert(
        "You have received a letter, good sir. " + 
        "I will have a quick lie-down and be on my way shortly."
      );
    }
    setTimeout(pollServerForMail, 1000);
  });
}());

在第一次發(fā)出請求,服務(wù)器響應(yīng)之前,不會發(fā)生任何事。在響應(yīng)回來時(shí),才會繼續(xù)發(fā)出第二個(gè)請求。當(dāng)然,這也就意味著,兩個(gè)輪詢之間的時(shí)間超過了1秒,這也依賴于各種各樣的因素,像網(wǎng)速和服務(wù)器的響應(yīng)速度等。但是,顯然的,這對我們要做的事來說并不算是什么問題。

例子

這里有兩個(gè)例子來更好的進(jìn)行說明。

var timesRun = 0;
var startTime = new Date().getTime();

var doStuff = function () {
  var now = new Date().getTime();

  // 只跑5次
  if (++timesRun == 5) clearInterval(timer);

  console.log("Action " + timesRun + " started " + (now - startTime) + "ms after script start");

  // Waste some time
  for (var i = 0; i < 100000; i++) {
    document.getElementById("unobtanium");
  }

  console.log("and took " + (new Date().getTime() - now) + "ms to run.");
};

var timer = setInterval(doStuff, 1000);

下面是結(jié)果

Action 1 started 1000ms after script start
and took 8ms to run.
Action 2 started 2000ms after script start
and took 8ms to run.
Action 3 started 3004ms after script start
and took 6ms to run.
Action 4 started 4002ms after script start
and took 6ms to run.
Action 5 started 5000ms after script start
and took 6ms to run.

這里并沒有多大的意外。這段代碼中間的循環(huán)花了一點(diǎn)時(shí)間,但是setInterval依然很嚴(yán)格的執(zhí)行了它的計(jì)劃。在一秒的間隔之間,開始時(shí)間之間并沒有一點(diǎn)空隙。

現(xiàn)在是setTimeout-loop的例子

var timesRun = 0;
var startTime = new Date().getTime();

var doStuff = function () {
  var now = new Date().getTime();

  console.log("Action " + (timesRun + 1) + " started " + (now - startTime) + "ms after script start");

  // Waste some time
  for (var i = 0; i < 100000; i++) {
    document.getElementById("unobtanium");
  }

  console.log("and took " + (new Date().getTime() - now) + "ms to run.");

  // Run only 5 times
  if (++timesRun < 5) {
    setTimeout(doStuff, 1000);
  }
};

setTimeout(doStuff, 1000);

輸出結(jié)果

Action 1 started 1010ms after script start
and took 8ms to run.
Action 2 started 2021ms after script start
and took 8ms to run.
Action 3 started 3031ms after script start
and took 5ms to run.
Action 4 started 4037ms after script start
and took 6ms to run.
Action 5 started 5043ms after script start
and took 6ms to run.

這里也并沒有太多的意外。我們已經(jīng)知道setTimeout-loop并不會嚴(yán)格的執(zhí)行計(jì)劃,而是在函數(shù)下一次調(diào)用之前,會給函數(shù)它足夠的時(shí)間執(zhí)行它里面的代碼。

結(jié)論

不要使用setInterval,如果你在乎你的時(shí)間。setTimeout-loop可以給你足夠的時(shí)間控制你的腳本和回調(diào),

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://m.specialneedsforspecialkids.com/yun/80888.html

相關(guān)文章

  • 徹底弄懂 JavaScript 執(zhí)行機(jī)制

    摘要:關(guān)于這部分有嚴(yán)格的文字定義,但本文的目的是用最小的學(xué)習(xí)成本徹底弄懂執(zhí)行機(jī)制,所以同步和異步任務(wù)分別進(jìn)入不同的執(zhí)行場所,同步的進(jìn)入主線程,異步的進(jìn)入并注冊函數(shù)。宏任務(wù)微任務(wù)第三輪事件循環(huán)宏任務(wù)執(zhí)行結(jié)束,執(zhí)行兩個(gè)微任務(wù)和。 不論你是javascript新手還是老鳥,不論是面試求職,還是日常開發(fā)工作,我們經(jīng)常會遇到這樣的情況:給定的幾行代碼,我們需要知道其輸出內(nèi)容和順序。 因?yàn)閖avascr...

    gyl_coder 評論0 收藏0
  • setTimeout 或者 setInterval關(guān)于 Javascript 計(jì)時(shí)器:需要知道

    摘要:所以,我們可以將理解為計(jì)時(shí)結(jié)束是執(zhí)行任務(wù)的必要條件,但是不是任務(wù)是否執(zhí)行的決定性因素。的意思是,必須超過毫秒后,才允許執(zhí)行。 先來回答一下下面這個(gè)問題:對于 setTimeout(function() { console.log(timeout) }, 1000) 這一行代碼,你從哪里可以找到 setTimeout 的源代碼(同樣的問題還會是你從哪里可以看到 setInterval 的...

    Warren 評論0 收藏0
  • 這一次,徹底弄懂 JavaScript 執(zhí)行機(jī)制

    摘要:事件完成,回調(diào)函數(shù)進(jìn)入。主線程從讀取回調(diào)函數(shù)并執(zhí)行。終于執(zhí)行完了,終于從進(jìn)入了主線程執(zhí)行。遇到,立即執(zhí)行。宏任務(wù)微任務(wù)第三輪事件循環(huán)宏任務(wù)執(zhí)行結(jié)束,執(zhí)行兩個(gè)微任務(wù)和。事件循環(huán)事件循環(huán)是實(shí)現(xiàn)異步的一種方法,也是的執(zhí)行機(jī)制。 本文的目的就是要保證你徹底弄懂javascript的執(zhí)行機(jī)制,如果讀完本文還不懂,可以揍我。不論你是javascript新手還是老鳥,不論是面試求職,還是日常開發(fā)工作...

    dreambei 評論0 收藏0
  • js 執(zhí)行機(jī)制 事件循環(huán)

    摘要:事件完成,回調(diào)函數(shù)進(jìn)入。我們來分析一段較復(fù)雜的代碼,看看你是否真的掌握了的執(zhí)行機(jī)制第一輪事件循環(huán)流程分析如下整體作為第一個(gè)宏任務(wù)進(jìn)入主線程,遇到,輸出。宏任務(wù)微任務(wù)第三輪事件循環(huán)宏任務(wù)執(zhí)行結(jié)束,執(zhí)行兩個(gè)微任務(wù)和。 關(guān)于JavaScript 首先js是單線程的,執(zhí)行任務(wù)肯定是一個(gè)接著一個(gè)。在最新的html5中提出了web-worker,但是JavaScript是單線程這一核心沒有改變,一...

    JackJiang 評論0 收藏0
  • JS忍者秘籍中定時(shí)器機(jī)制詳解

    摘要:設(shè)置和清除定時(shí)器直接引用忍者秘籍中的圖片注意定時(shí)器的時(shí)間間隔設(shè)為,也會有幾毫秒的延遲。以上參考資料忍者秘籍第章馴服線程和定時(shí)器 showImg(https://segmentfault.com/img/remote/1460000015353524?w=1024&h=681); 前言 前段時(shí)間剛看完《JS忍者秘籍》,雖說是15年出版的,有些東西是過時(shí)了,但像對原型鏈、閉包、正則、定時(shí)器...

    keelii 評論0 收藏0

發(fā)表評論

0條評論

最新活動
閱讀需要支付1元查看
<