2010-08-02 1 views
2

Это js примет значение, вычитает из него сумму X и затем подсчитает до этого значения.Javascript Loop & setInterval

Я попытался выполнить эту задачу, выполнив простой цикл while, но я не смог заставить его работать.

Мне было интересно, может ли кто-нибудь прокомментировать, как и почему метод while while ниже не работает.

Это единственный способ, которым я мог заставить его работать:

function _initCountUpUsers() 
{ 
    var totalUsers = $('#totalUsers'); 
    var ceiling = parseInt(totalUsers.html()); 
    var floor = ceiling - 10; 

    function updateTotalUsers() 
    { 
     if(floor < ceiling) 
     { 
      totalUsers.html(floor); 
      floor++; 
     } 
    } 

    window.setInterval(updateTotalUsers, 1000, floor); 
} 

Нерабочий Хотя метод:

function _initCountUpUsers() 
{ 
    var totalUsers = $('#totalUsers'); 
    var ceiling = parseInt(totalUsers.html()); 
    var floor = ceiling - 10; 

    function updateTotalUsers() 
    { 
     totalUsers.html(floor); 
     floor++; 
    } 

    while(floor < ceiling) 
    { 
     window.setInterval(updateTotalUsers, 1000, floor);  
    } 

} 
+0

Причина, по которой я хотел исследовать метод while (или даже for for), состоял в том, что я думал, что это будет лучшая практика или более академичный способ делать что-то. – doremi

+0

Это было бы чище, но это не реально.К счастью, JavaScript довольно гибкий - вы, вероятно, можете придумать что-то, что будет ближе к тому, что вы хотите (см. Мой обновленный ответ). – Shog9

ответ

3

Я не знаю, почему вы не хотите придерживаться первого метода, но ...

while(floor < ceiling) 
{ 
    window.setInterval(updateTotalUsers, 1000, floor);  
} 

Это собирается начать 10 отдельных таймеров, каждый набор стрелять один раз в во-вторых, каждый набор, чтобы увеличить этаж и обновить totalUsers, и ни один из них никогда не заканчивается. Если они будут стрелять, вы увидите, что счет увеличивается на десять в секунду, а в первом - на один. Тем не менее, ни один из них не начнет стрелять, так как вы будете навечно ждать этаж, чтобы достичь потолка!

JavaScript однопоточный. События (включая таймеры) помещаются в очередь во время выполнения скрипта. Таким образом, ваш цикл while никогда не будет завершен, потому что события таймера, которые будут его обновлять, будут ждать, пока он не завершит выполнение!

Даже если бы это было не так, у вас все равно было бы десять таймеров, работающих навсегда.

Вы были на правильном пути своим первым методом. Вам просто нужно, чтобы остановить таймер:

function _initCountUpUsers() 
{ 
    var totalUsers = $('#totalUsers'); 
    var ceiling = parseInt(totalUsers.html()); 
    var floor = ceiling - 10; 

    function updateTotalUsers() 
    { 
     if(floor < ceiling) 
     { 
      totalUsers.html(floor); 
      floor++; 
     } 
 else { window.clearInterval(timerID); // stop firing the timer once per second } 
    } 

    var timerID = window.setInterval(updateTotalUsers, 1000, floor); 
}

Если вы ищете немного очистителя/менее подверженные ошибкам способа написания этого, просто закодировать себя немного вспомогательную процедуру:

function while_interval(proc, int) 
{ 
    var timerID = setInterval(function() 
    { 
    if (!proc()) clearInterval(timerID); 
    }, int); 
} 

. ..и называют это так:

while_interval(function() 
{ 
    if (floor < ceiling) 
    { 
    totalUsers.html(floor); 
    floor++; 
    return true; 
    } 
}, 1000); 

Это позволяет абстрагироваться от крошечную домашнего хозяйства кода, но что более важно, что заставляет вас сознательно вернуть true до тех пор, как вы хотите й e, чтобы продолжить выполнение.

+0

хорошая рутина в нижней части вашего сообщения, и я ее скопировал/вставлял - но есть ошибка: где вы говорите «clearTimer (timerID)»; он должен быть «clearInterval (timerID)»; –

+0

Спасибо @ Andy! Годы спустя, кто-то наконец замечает - исправлено! Не стесняйтесь предлагать изменения, которые исправляют такие тривиальные ошибки, как btw. – Shog9

-1
function _initCountUpUsers() 
{ 
    var totalUsers = $('#totalUsers'), 
     ceiling = parseInt(totalUsers.html()), 
     floor = cieling - 10, 
     intRef = null; 

    function updateTotalUsers() 
    { 
     if(floor < ceiling) 
     { 
      totalUsers.html(floor); 
      floor++; 
     } 
     else { 
      window.clearInterval(intRef); 
     } 
    } 

    intRef = window.setInterval(updateTotalUsers, 1000); 
} 

или

function _initCountUpUsers() 
{ 
    var totalUsers = $('#totalUsers'); 
    var ceiling = parseInt(totalUsers.html()); 
    var floor = cieling - 10; 
    var int; 

    function updateTotalUsers() 
    { 
     if(floor < ceiling) 
     { 
      totalUsers.html(floor); 
      floor++; 
      window.setTimeout(updateTotalUsers, 1000); 
     } 
    } 

    window.setTimeout(updateTotalUsers, 1000); 
} 
+0

Да, это тот метод, который, как он сказал, работал ... И если вы собираетесь переключиться на setTimeout, вероятно, стоит добавить дополнительный код для настройки задержки таймера. – Shog9

Смежные вопросы