Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Data Structures and Algorithms in C++ 2e (На ру...docx
Скачиваний:
0
Добавлен:
01.07.2025
Размер:
2.37 Mб
Скачать

3.5. Рекурсия 137

Интересная работа сделана рекурсивной функцией drawTicks, который тянет

последовательность тиканья в пределах некоторого интервала. Его единственный аргумент - продолжительность тиканья, связанная с центральным тиканьем интервала. Считайте английского правителя с главной продолжительностью тиканья 5 показанными в рисунке 3.17 (b). Игнорируя линии, содержащие 0 и 1, давайте рассмотрим, как потянуть последовательность тиканья, находящегося между этими линиями. У центрального тиканья (в 1/2 дюйма) есть длина 4. Заметьте, что два образца тиканья выше и ниже этого центрального тиканья идентичны, и у каждого есть центральное тиканье длины 3. В

общий, интервал с центральной продолжительностью тиканья L³ 1 составлен из следующего:

• Интервал с центральной продолжительностью тиканья L- 1 • Единственное тиканье длины L • Интервал с центральной продолжительностью тиканья L- 1

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

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

луг drawTicks (L- 1) рекурсивно. Средний шаг выполнен, звоня

функция drawOneTick (L). Эту рекурсивную формулировку показывают в Кодексе Frag-

ment 3.37. Как в примере факториала, у кодекса есть основной случай (когда L = 0). В этом случае мы сделали два рекурсивных звонка к функции.

//одно тиканье с дополнительной этикеткой

пустота drawOneTick (интервал tickLength, интервал tickLabel =-1)

для (интервал i = 0; я <tickLength; я ++)

единое время co <<«-»; если (tickLabel> = 0) суд <<«» <<tickLabel; единое время co <<«\n»;

пустота drawTicks (интервал tickLength) //привлекают тиканье данной длины

если (tickLength> 0) //останавливаются, когда длина спадает 0

drawTicks (tickLength-1); //рекурсивно привлекают оставленное тиканье

drawOneTick (tickLength); //привлекают тиканье центра

drawTicks (tickLength-1); //рекурсивно привлекают правильное тиканье



пустота drawRuler (интервал nInches, интервал majorLength)//привлекают всего правителя

drawOneTick (majorLength, 0); //привлекают тиканье 0 и его этикетку

для (интервал i = 1; я <= nInches; я ++)

drawTicks (majorLength-1); //привлекают тиканье для этого дюйма

drawOneTick (majorLength, i); //привлекают тиканье i и его этикетка

Кодовый Фрагмент 3.37: рекурсивное внедрение функции, которая привлекает правителя.

138

Глава 3. Множества, связанные списки и рекурсия

Иллюстрирование Рисунка Правителя, используя След Рекурсии

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

След для drawTicks более сложен, чем в примере факториала, однако, потому что каждый случай сделал два рекурсивных звонка. Чтобы иллюстрировать это, мы показываем след рекурсии в форме, которая напоминает о схеме для документа. Посмотрите рисунок 3.18.

Рисунок 3.18: частичная рекурсия прослеживает для требования drawTicks (3). Второй образец призывов drawTicks (2) не показывают, но это идентично первому.

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