Рекурсивная функция в C (для печати пирамиды #) - PullRequest
1 голос
/ 07 апреля 2020

Я следую за знаменитым курсом CS50.

Во время урока учитель показал программу, которая распечатывала пирамиду высоты, заданную в качестве ввода от пользователя:

#include <cs50.h>
#include <stdio.h>

void pyramid(int n);

int main (void)
{
    int height = get_int("height:");
    pyramid(height);
    return 0;
}

void pyramid(int n)
{
    if (n==0)
    {
        return;
    }
    pyramid(n-1);

    for (int i=0; i<n;i++)
    {
        printf("#");
    }
    printf("\n");
}

Может кто-нибудь объяснить мне, что делает пирамида рекурсивной функции? Я отлаживаю его и вижу, что если входные данные проверяют, равно ли оно 0, то они вызывают себя до n == 0 и возвращаются. После этого отладчик переходит к l oop для и делает это n раз.

Следуя пути лайнера, он не должен go к для l oop. Зачем это нужно?

Большое спасибо за помощь!

Ответы [ 2 ]

1 голос
/ 07 апреля 2020

После установки некоторого значения height вызывается функция piramid. Если значение height равно 0, функция завершается. В противном случае он вызывает себя с уменьшенным аргументом height, что позволяет печатать каждый уровень пирамиды. Как вы можете видеть в теле void piramid(int n), оно сначала вызывает себя, а затем печатает n «блоки».

Допустим, мы работаем с height = n и попытаемся проанализировать, что происходит (каждая точка - это еще один шаг):

  • piramid(n) вызовы:
  • piramid(n-1) звонки:
  • piramid(n-2) звонки:
  • ...
  • piramid(1) звонки:
  • piramid(0) - ничего не возвращается, это это последний рекурсивный вызов piramid, поэтому мы начинаем возвращаться: в нашем случае это означает, что мы печатаем хэши в порядке сверху вниз:
  • # печатается, так как piramid(1) включен вершина стека, и после того, как мы распечатаем его, мы его выталкиваем, поэтому piramid(2) становится первым элементом сверху
  • ## печатаются, piramid(2) находится на вершине стека, мы выталкиваем его и продолжаем работать с другими вызовами таким же образом,
  • ...
  • (n-1) # печатаются, мы выталкиваем его из стека,
  • n # напечатано, наш стек теперь пуст.
1 голос
/ 07 апреля 2020

Чтобы сделать его понятным, давайте рассмотрим пример с небольшим числом:

#include <stdio.h>

void piramid (int n);

int
main (void)
{
  piramid (2);
}

void
piramid (int n)
{
  if (n == 0)
    {
      return;
    }
  piramid (n - 1);

  for (int i = 0; i < n; i++)
    {
      printf ("#");
    }
  printf ("\n");
}

Что он делает:

  • основные вызовы piramid (2)
  • piramid (2) вызывает piramid (1), однако piramid (2) не закончил sh, как вы сказали
  • piramid (1) вызывает piramid (0)
  • piramid (0) ничего не делает, так как возвращается немедленно
  • piramid (1) заканчивает и печатает #
  • piramid (2) заканчивает и печатает ##

Если n будет больше, это будет следуйте этому, но с дополнительными шагами

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

...