美文网首页
廖雪峰 | 3.2 递归函数

廖雪峰 | 3.2 递归函数

作者: 苦哈哈的柠檬水 | 来源:发表于2022-04-16 11:11 被阅读0次

1,定义
一个函数在内部调用自身本身,这个函数就是递归函数。
例如,计算阶乘n! = 1 x 2 x 3 x ... x n

>>> def fact(n):
...     if n == 1:
...         return 1
...     return n*fact(n-1)
...
>>> fact(1)
1
>>> fact(3)
6

2,栈溢出
(1)栈溢出,stack overflow,递归调用的次数过多,会导致栈溢出。例如,fact(1000)

>>> fact(1000)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 4, in fact
  File "<stdin>", line 4, in fact
  File "<stdin>", line 4, in fact
  [Previous line repeated 995 more times]
  File "<stdin>", line 2, in fact
RecursionError: maximum recursion depth exceeded in comparison

(2)尾递归优化,是解决递归调用栈溢出的方法。

  • 尾递归是指,在函数返回的时候,调用自身本身,并且,return语句不能包含表达式。例如,fact(n)函数由于return n * fact(n - 1)引入了乘法表达式,所以就不是尾递归。
  • 修改成尾递归方式,主要是要把每一步的乘积传入到递归函数中:
def fact(n):
    return fact_iter(n, 1)

def fact_iter(num, product):
    if num == 1:
        return product
    return fact_iter(num - 1, num * product)

fact(100)#依旧报错
  • 尾递归调用时,如果做了优化,栈不会增长,因此,无论多少次调用也不会导致栈溢出。
  • 遗憾的是,大多数编程语言没有针对尾递归做优化,Python解释器也没有做优化,所以,即使把上面的fact(n)函数改成尾递归方式,也会导致栈溢出。
    3,练习:汉诺塔游戏
    请编写move(n, a, b, c)函数,它接收参数n,表示3个柱子A、B、C中第1个柱子A的盘子数量,然后打印出把所有盘子从A借助B移动到C的方法,例如:
# -*- coding: utf-8 -*-
def hanoi(n, a, b, c):
    if n == 1:
        print(a, '-->', c)
    else:
        hanoi(n-1, a, b, c)
        print(a, '-->', c)
        hanoi(n-1, b, a, c)

#测试
>>> from hanoi import hanoi
>>> hanoi(3, 'A', 'B', 'C')
A --> C
A --> C
B --> C
A --> C
B --> C
B --> C
A --> C

相关文章

  • 廖雪峰 | 3.2 递归函数

    1,定义一个函数在内部调用自身本身,这个函数就是递归函数。例如,计算阶乘n! = 1 x 2 x 3 x ... ...

  • Python:3.函数

    调用函数 定义函数 函数的参数 递归函数 参考 廖雪峰的Python教程

  • python学习4

    学廖雪峰老师的python教程笔记。 1、递归函数 函数内部调用该函数本身,比循环逻辑简单 注意防止栈溢出 尾递归...

  • Python汉诺塔算法解析

    昨天看廖雪峰的Python教程,看到了递归函数,具体的递归函数看他讲的就可以,最好自己好好研究一下递归函数是干啥的...

  • 汉诺塔解体思路

    前言 前几天在廖雪峰老师的博客上学习Python时,在递归函数中廖老师出了这么一个问题: 汉诺塔的移动可以用递归函...

  • 算法图解系列之递归[03]

    3 递归 3.1 递归<函数> 3.2 基线条件和递归条件 3.3 递归调用栈

  • 廖雪峰JavaScript函数

    函数定义和调用 abs.length; 可以检测函数内有多少变量 arguments 只在函数内部起作用,并且永远...

  • 廖雪峰 | 3.0 函数

    1 调用函数 2 定义函数 3 函数的参数 4 递归函数 1 调用函数 1,使用函数时,需要知道函数的名称和参数2...

  • (二)JavaScript 函数

    本文是大神廖雪峰的JavaScript教程学习笔记。并不是教程,如有需要,请前往廖雪峰大神大博客. 一、函数定义和...

  • JavaScript | 函数与方法

    Reference : JavaScript教程 - 廖雪峰的官方网站 JavaScript函数基础 定义函数 在...

网友评论

      本文标题:廖雪峰 | 3.2 递归函数

      本文链接:https://www.haomeiwen.com/subject/cgmvsrtx.html