递归,就是在运行的过程中调用自己。他有两个要点
1. 调用自身,因为子问题须与原始问题为同样的事,且更为简单;
2. 有终止条件,设置自身正确的返回值,因为不能无限制地调用本身,否则无法退出;
他的缺点是
1. 速度不太快
2. 若调用自身深度太多,容易挂掉,占用过多栈内存。
所以虽然递归写起来比较简单,接近正常的思维,但是不是什么问题都用递归来解决,如下的阶乘,斐波那契数列和汉诺塔在很小的是数据递归还是可以的,但是数据一大,就不太行了。
不过,这不影响,并不是说递归就不能用了;若是能预先明确层级和深度不是很大的情况下,使用递归还是很简单又方便的,比如很多树形结构,就很适合用递归,只要你能了解到你的树形结构的层级不是无限极的。
阶乘:0!=1,1!=(1-1)! * 1 = 1, (n-1)!= (n-2)! * (n -1) , n!=(n-1)!×n,
非递归的阶乘
def factorial(n):
if n <= 0:
print("非正整数!")
return -1
result = n
# 遍历1~n,累乘
for i in range(1, n):
result *= i
return result
number = int(input("输入一个>0的正整数:"))
factorialNumber = factorial(number)
if factorialNumber != -1:
print('非递归的阶乘:%d 的阶乘是:%d' % (number, factorialNumber))
递归的阶乘
# 1. 调用函数自身
# 2. 设置自身正确的返回值,有截止条件
def factorial(n):
if n <= 0:
print("非正整数!")
return -1
if n == 1:
return 1
else:
return factorial(n - 1) * n
number = int(input("输入一个>0的正整数"))
factorialNumber = factorial(number)
if factorialNumber != -1:
print('%d 的阶乘是:%d' % (number, factorialNumber))
他们的差别只有这一段代码,循环累乘,保留中间结果,直至最终的结果;或者设置截止条件n为1,循环调用自身。
result = n
# 遍历1~n,累乘
for i in range(1, n):
result *= i
return result
if n == 1:
return 1
else:
return factorial(n - 1) * n
斐波那契数列的公式:F(1)=1,F(2)=1, F(n)=F(n-1)+F(n-2)(n>=3,n∈N*)
非递归的斐波那契数列
def fibonacci(n):
if n <= 0:
print("非正整数!")
return -1
n1 = 1
n2 = 1
n3 = 1
# 1、1、2(1+1)、3(2+1)、5(3+2)、8(5+3)、13(8+5)、21(13+8)
# 从第三位3开始=前两位相加,使用n1和n2来表示前两位,往后循环,n3变为n2,n2变为n1
while (n - 2) > 0:
n3 = n2 + n1
n1 = n2
n2 = n3
n = n - 1
return n3
number = int(input("输入一个>0的正整数"))
result = fibonacci(number)
if result != -1:
print('%d 的斐波那契数列是:%d' % (number, result))
递归的斐波那契数列
def fibonacci(n):
if n <= 0:
print("非正整数!")
return -1
# 截止条件
if n == 1 or n == 2:
return 1
# 调用自身
else:
return fibonacci(n - 1) + fibonacci(n - 2)
number = int(input("输入一个>0的正整数"))
result = fibonacci(number)
if result != -1:
print('%d 的斐波那契数列是:%d' % (number, result))
这两段相比,使用递归确实要简单很多;当n=35的时候,递归就已经很慢了;当n=1000的时候,就直接开始报错了。而循环的还是可以很快就算出结果,1000也是秒出;
n1 = 1
n2 = 1
n3 = 1
# 1、1、2(1+1)、3(2+1)、5(3+2)、8(5+3)、13(8+5)、21(13+8)
# 从第三位3开始=前两位相加,使用n1和n2来表示前两位,往后循环,n3变为n2,n2变为n1
while (n - 2) > 0:
n3 = n2 + n1
n1 = n2
n2 = n3
n = n - 1
return n3
# 截止条件
if n == 1 or n == 2:
return 1
# 调用自身
else:
return fibonacci(n - 1) + fibonacci(n - 2)
递归的汉诺塔
def hanoi(n, source, middle, target):
if n <= 0:
print("非正整数!")
return -1
if n == 1:
print(source, '--->', target)
else:
# 将n-1个块,从A移动到B,通过C;
hanoi(n - 1, source, target, middle)
# 将第n个块,直接从A移动到C,
print(source, '--->', target)
# 将剩下的n-1个块,从B移到C,通过A;
hanoi(n - 1, middle, source, target)
number = int(input("输入一个>0的正整数"))
# 将A移动到C,通过B
result = hanoi(number, "A", "B", "C")