Разница между setTimeout (fn, 0) и setTimeout (fn, 1)? - PullRequest
28 голосов
/ 01 декабря 2011

Источник jquery использует setTimeout с обоими 0 и 1 в качестве второго аргумента.У меня сложилось впечатление, что они оба означают «выполнить функцию как можно скорее».

Это правильно?Есть ли разница между ними?

Ответы [ 6 ]

29 голосов
/ 01 декабря 2011

setTimeout имеет минимальное время ожидания 4 мс.Таким образом, на самом деле разница между ними отсутствует .

Если текущая запущенная задача - это задача, созданная методом setTimeout (), и время ожидания меньше 4,затем увеличьте время ожидания до 4.

Спецификация

РЕДАКТИРОВАТЬ: Как указано Ахмадом в комментарияхТеперь спецификация изменилась, поэтому ответом будет: «Это зависит».

13 голосов
/ 22 июня 2016

Я думаю, что ответ "Это зависит" сейчас.

Мы можем запустить код в разных платформах и браузерах:

function setTimeouts() {
  setTimeout(function() { console.log(2); }, 2);
  setTimeout(function() { console.log(1); }, 1);
  setTimeout(function() { console.log(0); }, 0);
}

for (var i = 0; i < 10; i++) {
  setTimeouts();
}
  1. Для Node.js 0 преобразуется в 1, поэтому они точно такие же: https://github.com/nodejs/node/blob/master/lib/timers.js#L319,, и результат может быть:

    1
    0
    1
    0
    1
    0
    1
    0
    1
    0
    1
    0
    1
    0
    1
    0
    1
    0
    1
    0
    2
    2
    2
    2
    2
    2
    2
    2
    2
    2
    
  2. Для Chrome результат очень похож на Node.js

  3. Для Firefox большая часть 0 будет напечатана до 1:

    0
    0
    0
    0
    0
    0
    0
    0
    0
    0
    1
    1
    1
    1
    1
    1
    1
    1
    1
    1
    2
    2
    2
    2
    2
    2
    2
    2
    2
    2
    
4 голосов
/ 24 апреля 2013

Я не уверен, что приведенные ответы верны.Запустив следующий код в Chrome, 0 явно вызывает связанную функцию быстрее (просто переключите значения таймера между 0 и 1):

console.log("A");
console.log("B");
var start = new Date().getTime();
setTimeout(function() {
    console.log(new Date().getTime() - start);
}, 0);
console.log("C");
console.log("D");

0, кажется, делаетчто-то вроде setImmediate в NodeJS, помещающее инструкцию в конец текущего стека вызовов, в то время как 1 вызывает все, что реализация рассматривает как минимальное значение.

2 голосов
/ 01 декабря 2011

Программно и в вычислительном отношении есть разница, но вы не увидите разницу при ее выполнении, так как она равна 1ms.

Я полагаю, что если для тайм-аута установлено значение 1ms, он приостанавливает этот сценарий и позволяет другим сценариям запускаться. И, как вы, вероятно, знаете, javascript является однопоточным, так что это может быть вашей причиной прямо здесь.

EDIT:

Благодаря @molf, который исправил мои мысли, может показаться, что установка его на 0 мс - просто уловка, чтобы заставить его работать в следующем тике цикла событий.

1 голос
/ 01 декабря 2011

По причинам, по которым setTimeout (fn, 0) или setTimeout (fn, 1) необходимы, посмотрите Почему setTimeout (fn, 0) иногда полезен?

По сути этоозначает, что этот метод не очень актуален для выполнения по сравнению с другими задачами браузера, такими как рендеринг страницы.Более того, js-код будет запускаться после завершения ожидающих задач.С практической точки зрения, нет никакой разницы между использованием 0 или 1. Это просто выбор программиста.В идеале число, выбранное кодерами, должно быть меньше 4, что может быть связано с причиной, указанной Amaan.

btw, для базовой информации о таймерах Javascript, обратитесь к http://ejohn.org/blog/how-javascript-timers-work/

0 голосов
/ 01 декабря 2011

Это просто пример плохой практики кода в исходном коде jQuery.

Вот и все.Нет оснований отдавать предпочтение 0 над 1 или наоборот.

Вызывать ошибку jQuery, исправить или нормализовать ее для использования одного или другого.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...