среда, 17 июля 2013 г.

Замена setInterval на setTimeout при выполнении асинхронных операций

Используйте setTimeout() вместо setInterval() для ускорения серилизации данных.

Представьте, что вам нужно выполнять функцию, которая периодически осуществляет открытие и считывание данных из log-файла.

setInterval(function(){
    myAsyncParseFile(function(){
        console.log('parsing finished');
    });
}, 1000);

Однако нужно быть уверенным, что выполнении нескольких таких функций не произойдет в одно и тоже время.
Но этого нельзя гарантировать, если вы используете функцию setInterval().

Для того, чтобы быть уверенным, что выполнение следующей функции не совпадет с выполнением предыдущей используется следующий код с функцией setTimeout внутри замыкания:

(function shedule (){
    setTimeout(function(){
        myAsyncParseFile(function(){
            console.log('parsing finished');
            shedule();
        });
    }, 1000);
})();

Здесь мы декларируем функцию-замыкание shedule(), которую сразу же запускаем.
Функция shedule запускает внутри себя функцию setTimeout().
Через 1 секунду функция setTimeout выполняет асинхронную функцию myAsyncParseFile.
В асинхронную функцию myAsyncParseFile передается колбак-функция, которая будет выполнена в конце успешног завершения работы асинхронной функции.
В заключении своего выполнения колбак-функция вызывает внешнюю функцию shedule(), которая запускает опять всю цепочку выполнения через 1 секунду.
Таким образом данный код имитирует поведение функции setInterval(), но при этом гарантирует, что выполнение асинхронного кода не наложится и не произойдет одновременно.

По-другому этот код можно записать так:

function shedule () {
    setTimeout(function(){
        myAsyncParseFile(function(){
            console.log('parsing finished');
            shedule(); // Рекурсивный вызов функции самой себя.
        });
    }, 1000);
}

shedule ();

Комментариев нет:

Отправить комментарий