递归是指一个函数在自己的代码中调用自己的过程。你可以把它看作是完成一个循环结构的另一种方式。递归模式出现在现实世界的许多场景中,我们将在这里介绍一些 Python 中递归的例子。一个递归函数只是不断地调用自己,直到完成手头的问题。这带来了一个很好的观点,那就是要确保你的递归函数实际上在某个时刻终止并返回。否则,递归函数将永远运行,耗尽你的内存,并使你的计算机崩溃。有一个函数实际结束的步骤被称为中断条件。每次调用递归函数时,前一次调用的参数值都会存储在调用栈中。
递归实例1:向后数2
这里我们有一个名为backwardsby2的函数,它从一个初始数字开始,用2的步长来打印数字的倒序。破解条件是如果该数字小于或等于零。在这种情况下,我们只需打印 "零 "即可。如果不满足这个条件,该函数将使用当前的数字-2来调用自己。我们还初始化了一个列表,并添加了一个等于当前数字的笑脸表情符号。这样一来,随着倒数的发生,每次迭代都会出现相应数量的表情符号笑脸。我想你会同意,这是这个递归例子的一个重要特征。
def backwardsby2(num):
if num <= 0:
print('Zero!')
return
else:
emojismiles = []
for i in range(0, num):
emojismiles += '😃'
print(num, ' '.join(emojismiles))
backwardsby2(num - 2)
backwardsby2(9)
9 😃 😃 😃 😃 😃 😃 😃 😃 😃
7 😃 😃 😃 😃 😃 😃 😃
5 😃 😃 😃 😃 😃
3 😃 😃 😃
1 😃
Zero!
递归实例2:河内塔
河内塔是一个古老的谜题,据说起源于印度或越南。它涉及到在三根柱子上移动各种大小的圆环或圆盘。这个谜题的目标是将一个柱子上的所有圆环移到另一个柱子上,同时保持圆环的顺序不变。但是,你必须遵守谜题的规则,即每次只能移动一个权利,而且不能将环放在一个较小的环上面。这个谜题可以用Python中的递归来解决,所以让我们来看看它的实际效果吧!
def towerOfHanoi(numrings, from_pole, to_pole, aux_pole):
if numrings == 1:
print('Move ring 1 from', from_pole, 'pole to', to_pole, 'pole')
return
towerOfHanoi(numrings - 1, from_pole, aux_pole, to_pole)
print('Move ring', numrings, 'from', from_pole, 'pole to', to_pole, 'pole')
towerOfHanoi(numrings - 1, aux_pole, to_pole, from_pole)
numrings = 2
towerOfHanoi(numrings, 'Left', 'Right', 'Middle')
Move ring 1 from Left pole to Middle pole
Move ring 2 from Left pole to Right pole
Move ring 1 from Middle pole to Right pole
上面的输出显示了只有两个环时的步骤数。我们可以在使用三个环的情况下再次运行程序,你会发现解决河内塔的步骤数在增长。此外,你可以在可视化中查看过程中的每一步。
numrings = 3
towerOfHanoi(numrings, 'Left', 'Right', 'Middle')
Move ring 1 from Left pole to Right pole
Move ring 2 from Left pole to Middle pole
Move ring 1 from Right pole to Middle pole
Move ring 3 from Left pole to Right pole
Move ring 1 from Middle pole to Left pole
Move ring 2 from Middle pole to Right pole
Move ring 1 from Left pole to Right pole
河内塔的起始状态

将环1从左极移至右极

将环2从左极移至中极

将1号环从右杆移到中杆

将3号环从左杆移到右杆

将1号环从中间杆移至左杆

将2号环从中间杆移至右杆

将环1从左极移到右极

递归实例3:将一个数字设为一个幂数
我们可以使用递归来创建一个函数,计算一个数字乘以自己一定次数的值。当然,你已经看过很多次了。在数学中,将一个数字设为一个数字的幂,这是一个常见的操作。例如,2的四次方是16,2的五次方是32,以此类推。我们想把一个参数乘以一定的倍数。这意味着我们需要两个参数,一个是数字本身,另一个是它将被设置为的幂。破解条件是如果 **topwr**变量为零。这意味着我们已经完成了所有需要的乘法运算。正是这个函数递归调用自己的事实提供了一个循环行为。
def power(num, topwr):
if topwr == 0:
return 1
else:
return num * power(num, topwr - 1)
print('{} to the power of {} is {}'.format(4, 7, power(4, 7)))
print('{} to the power of {} is {}'.format(2, 8, power(2, 8)))
4 to the power of 7 is 16384
2 to the power of 8 is 256
递归实例4:阶乘函数
阶乘是将所有小于或等于一个给定数的整数相乘的过程。所以,5!相当于5*4*3*2*1,就是120。我们可以使用一个递归函数来为我们做这项工作。它只需要一个参数,即我们要应用阶乘的数字。对于突破条件,如果给定的参数已经达到零,我们就返回1的值。否则,我们返回数字乘以阶乘并递减数字值。
def factorial(num):
if (num == 0):
return 1
else:
return num * factorial(num - 1)
print('{}! is {}'.format(4, factorial(4)))
print('{}! is {}'.format(2, factorial(2)))
4! is 24
2! is 2
递归实例 5: 斐波那契数列
斐波那契数列在世界和所有自然界中随处可见。0、1、1、2、3、5、8、13、21、34等等的序列就是斐波那契序列。每一个连续的数字都是由前面的两个数字相加而得。下面是我们在 Python 中使用递归函数计算斐波那契数列的方法。它使用这个过程。
- 如果数字是0,那么答案就是0。
- 如果这个数字是1,那么答案就是1。
- 否则,答案就是前两个斐波那契数字的总和。
def fibonacci(n):
if n <= 1:
return n
else:
return fibonacci(n - 1) + fibonacci(n - 2)
number = 14
print('Fibonacci sequence:')
for i in range(number):
print(fibonacci(i))
Fibonacci sequence:
0
1
1
2
3
5
8
13
21
34
55
89
144
233
递归例6:从1到n的数字之和
我们可以用递归来找出从1到n的数字之和,如1+2+3+4+,等等。
def sumnums(n):
if n == 1:
return 1
return n + sumnums(n - 1)
print(sumnums(3))
print(sumnums(6))
print(sumnums(9))
6
21
45
递归实例7:反转一个字符串
这个例子很有趣。这里有反转字符串的递归函数,还有一些非常有趣的字符串,反转后会产生意想不到的结果
def reverse(string):
if len(string) == 0:
return string
else:
return reverse(string[1:]) + string[0]
reverseme = 'Desserts'
print(reverse(reverseme))
reverseme = 'Knits'
print(reverse(reverseme))
reverseme = 'Regal'
print(reverse(reverseme))
reverseme = 'Pupils'
print(reverse(reverseme))
reverseme = 'Smart'
print(reverse(reverseme))
reverseme = 'Pals'
print(reverse(reverseme))
reverseme = 'Straw'
print(reverse(reverseme))
reverseme = 'Time'
print(reverse(reverseme))
reverseme = 'Star'
print(reverse(reverseme))
stresseD
stinK
lageR
slipuP
tramS
slaP
wartS
emiT
ratS
Python 递归实例总结
递归函数直接或间接地调用自己,从而形成一个循环。这种循环一直持续到满足一个中断条件为止。它们可以被用来遍历任意形状的结构,或者用于一般的迭代。Python 支持递归,尽管在许多情况下它不一定是最简单或最有效的方法。在本教程中,我们看到了 Python 中递归的几个例子。把这些片段放在你的 IDE 中,在改变函数所提供的参数时对它们进行测试。这将有助于更好地理解它们如何工作。递归函数有一些需要注意的缺点。递归函数可能是低效的,因为它们占用了大量的内存和时间。除此之外,有时递归背后的逻辑很难遵循,使得调试问题很困难。