2016-12-31 5 views
9
int f(int n) 
{ 
    if (n <= 1) 
    { 
     return 1; 
    } 
    return f(n - 1) + f(n - 1); 
} 

Я знаю, что временная сложность O(2^n), и я понимаю, почему.Какова пространственная сложность этого кода?

Но я не понимаю, почему космическая сложность O(n). Мне сказали, что это потому, что в любой момент времени есть только n узлов, но для меня это не имеет смысла.

+3

Напишите формулу и решите ее. 'Память (n) = 1 + max (Память (n-1), Память (n-1))' –

+1

Этот вопрос лучше подходит для http://cs.stackexchange.com/ – Nayuki

ответ

13

Поскольку второй f(n-1) не может работать, пока первый не завершится (или наоборот - это то же самое). Первый вызов будет возвращен n раз, затем все они вернутся, так что он будет в общей сложности n кадрами стека. Тогда второй вызов будет делать то же самое.

Таким образом, он никогда не получает более глубоких уровней рекурсии уровней n, и это единственный вклад в пространственную сложность.

+1

Но откуда вы знаете, что это как операционная система реализует рекурсию? потенциально он может выполнять каждый вызов с потоками, каждый ждет других двух ... Я просто не понимаю, почему в худшем случае это может быть больше, чем O (n). Как я вижу, в общем случае это может быть O (n) – chris

+6

Сложные вычисления теоретические, не основанные на конкретной реализации, и этому концептуально нужен только один поток с последовательными рекурсивными вызовами. Если вы перепишете код, используя фактические потоки, сложность будет отличаться. – Barmar

+0

но это мой пункт. поскольку он не основан на конкретной реализации, вам нужно рассмотреть наихудший сценарий. не так ли? – chris

6

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

5

Нарисуйте дерево экспоненциальной временной сложности, а длина пути любого листа от корня дерева будет линейной. Этот линейный путь представляет собой пространственную сложность алгоритма. Алгоритм будет пересекать каждый из этих путей для решения проблемы, но в любой момент максимальное количество рекурсивных вызовов, хранящихся в стеке, будет линейным. Пример: для f(3)

  3 
    / \ 
    2  2 
    /\ /\ 
    1 1 1 1 

Максимальная длина от корня до листа равно O(n). Таким образом, сложность пространства также составляет O(n).

+0

Почему у вас разные значения в левом и правом поддеревах? Оба они вызываются с параметром «n-1». Может быть, вы думали, что он рассчитывает Фибоначчи? – Barmar

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