Как преобразовать рекурсивную функцию в зацикленную функцию с помощью Jquery / javascript - PullRequest
1 голос
/ 05 января 2012

Я пытаюсь сделать слайд-шоу с помощью Jquery, изображения циклически повторяются с помощью функции, которая вызывает себя каждые 5,5 секунд.Тем не менее, я пытаюсь избежать рекурсии, поскольку это очень дорого по сравнению с итеративными вызовами.И я предполагаю, что это является причиной того, что IE имеет значок непрерывной загрузки при загрузке моего слайд-шоу.Поэтому я хочу преобразовать следующую функцию в итеративную.

function playslides()
{

//hide previous slide
$(document.getElementById(t)).fadeOut("slow");


//reset slide index
calcSildes();

//show new slide
$(document.getElementById(t)).fadeIn("slow");

//recursive call after 5.5 sec
timer = setTimeout("playslides()", 5500);

}


//on page load...

$(document).ready(

playslides();

);

На данный момент мои два подхода таковы:

  1. создать цикл while внутри документа $ () .ready () и функция playslides () цикла.

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

Спасибо !!

Ответы [ 4 ]

5 голосов
/ 05 января 2012

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

Цитата Джона Резига , создателя jQuery:

На фундаментальном уровне важно понять, как работают таймеры JavaScript.Часто они ведут себя неинтуитивно из-за одного потока, в котором они находятся. Давайте начнем с изучения трех функций, к которым у нас есть доступ, которые могут создавать и манипулировать таймерами.

var id = setTimeout(fn, delay); - Инициирует один таймер, который будетвызвать указанную функцию после задержки.Функция возвращает уникальный идентификатор, с помощью которого таймер может быть отменен позднее.

var id = setInterval(fn, delay); - аналогично setTimeout, но постоянно вызывает функцию (с задержкой каждый раз), пока она не отменяется.

clearInterval(id);, clearTimeout(id); - принимает идентификатор таймера (возвращаетсяс помощью любой из вышеупомянутых функций) и останавливает обратный вызов таймера.

Используя setInterval, вы можете упростить свой код до следующего:

function playslides()
{
    //hide previous slide
    $(document.getElementById(t)).fadeOut("slow");

    //reset slide index
    calcSildes();

    //show new slide
    $(document.getElementById(t)).fadeIn("slow");
}

$(document).ready(function() {
     setInterval(playslides, 5500);
});
2 голосов
/ 05 января 2012

https://developer.mozilla.org/en/window.setInterval

var intervalID = window.setInterval(playslides, 5500);
1 голос
/ 05 января 2012

Это не рекурсивная функция. Рекурсивная функция продолжает создавать и сохранять свои копии в памяти до тех пор, пока не будет достигнут базовый случай, после чего стек раскручивается и возвращаются значения. Также должно быть изменение параметров в рекурсивном вызове, которое в конечном итоге приведет к базовому случаю.

PHP Пример:

function recursive_function($num){
    if ($num == 0){ //base case
        return 10;
    }else{
        return $num + recursive_function($num-1);
    }
}

recursive_function(5);//output is 25

Ваша функция просто создает новые таймеры, которые вызывают ту же функцию после того, как оригинал покинул память.

Удалите 'timer = setTimeout (playslides, 5500, $ element);' строка в функции playlides.

Заменить 'playslides ($ ("#" + t)); " вызовите функцию document.ready с:

timer = window.setInterval(function(){
    playslides($("#"+t));
}, 5500);

Вам нужно создать анонимную функцию для setinterval для правильной передачи параметров (для старых браузеров ... не в HTML5).

1 голос
/ 05 января 2012

Невозможно создать цикл с отложенными итерациями.

Единственная оптимизация - замена "playslides()" на playslides и кэширование объектов jQuery, которые ссылаются на один и тот же объект:

var timer;
function playslides($element) {
    //hide previous slide
    $element.fadeOut("slow");

    //reset slide index
    calcSildes();

    //show new slide
    $element.fadeIn("slow");

    //recursive call after 5.5 sec
    timer = setTimeout(playslides, 5500, $element);
}

// Bug fix too, wrap document.ready in `function(){
$(document).ready(function(){
    playslides($("#"+t));    
});
...