Можно ли это назвать рекурсивным? - PullRequest
8 голосов
/ 13 января 2010
function move() {

    pos = pos+1;

    t = setTimeout(move, 100); 
}

Это можно назвать рекурсивным? Если да, не могли бы вы предоставить какую-либо ссылку?

Ответы [ 9 ]

13 голосов
/ 13 января 2010

Нет, разница между рекурсией (func_a вызывает func_a) и косвенной рекурсией (func_a вызывает func_b, вызывает func_a) в том, что использование таймера для повторяющихся вызовов (развязка) не увеличивает стек, и предыдущее состояние теряется.

3 голосов
/ 13 января 2010

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

Рекурсия включает разбиение проблемы на более мелкие, похожие проблемы, пока вы не достигнете базового случая, а затем, возможно, объединение полученных результатов в решение. Здесь нет «меньшей» проблемы; это просто планирование того же самого обратного вызова, чтобы повториться через определенное время.

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

Например, это рекурсивно?

function state1() {
    doSomething();
    return "state2";
}

function state2() {
    doSomethingElse();
    return "state1";
}

var state = "state1";
while (true) {
    if (state == "state1") {
        state = state1();
    } else {
        state = state2();
    }
}

state1 и state1 каждый вызывает другого; так что в каком-то смысле это взаимная рекурсия. Он управляется итеративным циклом, поэтому его также можно считать итерацией.

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

function state1() {
    doSomething();
    state2();
}

function state2() {
    doSomething();
    state1();
}

Итак, действительно возникает вопрос: как вы различаете, является ли что-то рекурсивным? Делает ли тот факт, что одна функция вызывает себя снова, делает ее рекурсивной?

3 голосов
/ 13 января 2010

Нет. Функция вызывается внешним источником (таймером), поэтому она не является рекурсивной.

2 голосов
/ 13 января 2010

Я бы назвал это бесконечным циклом с задержкой.

Когда функция возвращается, она не возвращается в свой предыдущий экземпляр вызова, следовательно, нет глубокого "стека вызовов", как это обычно бывает в рекурсиях.

2 голосов
/ 13 января 2010

Код, о котором идет речь, не является рекурсией - так как код вызывается извне, а не как часть циклического пути кода к тому же вызову метода.

В Википедии есть отличная страница о рекурсии здесь: Википедия: рекурсия (информатика)

1 голос
/ 27 января 2010

технически это может быть ...

function move() {

    var $this = this;

    pos = pos+1;

    t = setTimeout($this, 100);
}

но я не вижу причин, почему вы хотите это сделать. и если вы действительно хотите стать глупым (и заблокировать ветку вашего браузера):

function move() {

    var now = +new Date;

    pos = pos+1;

    while( ( +new Date - now ) <= 100 ){ }

    move( );
}
1 голос
/ 13 января 2010

Итак, здесь f1 ("move") вызывает f2 ("setTimeout"), что, в свою очередь, снова вызывает f1. Хм .. это рекурсия, если f2 - функция обратного вызова. Но, если f2 устанавливает какое-то свойство, например, «тайм-аут». Это не рекурсия.

0 голосов
/ 13 января 2010

Да, это так .. но это можно назвать косвенной рекурсией ..

Пример

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

    function factorial (n)
  {
        if(n==0)
   { 
        return(1);
   }

     return (n * factorial (n-1) ); 
  }

Точно так же другие говорили ... функция, вызывающая себя ..

0 голосов
/ 13 января 2010

Нет, функция не вызывает сама себя. Было бы рекурсивно, если бы функция вызывала себя в теле перемещения.

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