Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/330.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 递归函数(基本)_Python_Recursion - Fatal编程技术网

Python 递归函数(基本)

Python 递归函数(基本),python,recursion,Python,Recursion,我正在处理一个相当基本的函数,我发现很难弄清楚为什么我会得到输出 def mystery(n): print(n) if n < 4: mystery(n + 1) print(n) mystery(1) 我想我对输出的第一部分很清楚,n

我正在处理一个相当基本的函数,我发现很难弄清楚为什么我会得到输出

def mystery(n):    
    print(n)     
    if n < 4:     
        mystery(n + 1)    
    print(n)        

mystery(1)
我想我对输出的第一部分很清楚,n<4,所以我们每次加1,然后当我们达到4时,函数跳过if部分并再次打印(n),它是4。然后我有点不知所措,尽管为什么输出倒数为1。我猜我忽略了递归中一些非常明显的部分,谢谢你的帮助

每次
神秘(n+1)
完成时,将调用下一个
打印(n)

也许下面的代码更清楚:

def mystery(n):
    print('\t' * n + 'enter mystery ' + str(n))
    if n < 4:
        print('\t' * n + 'before mystery(n+1) ' + str(n))
        mystery(n + 1)
    print('\t' * n + 'after mystery ' + str(n))

mystery(1)

为了帮助OP可视化正在发生的事情,几个print语句可以显示代码的实际流程:

def mystery(n):    
    print(f"First print: {n}")
    if n < 4:
        print(f"n < 4 == True, n: {n}")
        mystery(n + 1)
    else:
        print(f"n < 4 == False, n: {n}")
    print(f"Second print: {n}")

mystery(1)
def神秘(n):
打印(f“第一次打印:{n}”)
如果n<4:
打印(f“n<4==True,n:{n}”)
神秘(n+1)
其他:
打印(f“n<4==False,n:{n}”)
打印(f“第二次打印:{n}”)
神秘(1)
输出:

enter mystery 1
before mystery(n+1) 1
    enter mystery 2
    before mystery(n+1) 2
        enter mystery 3
        before mystery(n+1) 3
            enter mystery 4
            after mystery 4
        after mystery 3
    after mystery 2
after mystery 1
First print: 1
n < 4 == True, n: 1
First print: 2
n < 4 == True, n: 2
First print: 3
n < 4 == True, n: 3
First print: 4
n < 4 == False, n: 4
Second print: 4
Second print: 3
Second print: 2
Second print: 1
第一次打印:1
n<4==真,n:1
首次印刷:2
n<4==真,n:2
首次印刷:3
n<4==真,n:3
首次印刷:4
n<4==False,n:4
第二次印刷:4
第二次印刷:3
第二次印刷:2
第二次印刷:1

将其视为一个调用树:

mystery(1)
  print(1) - first print
  mystery(1 + 1 = 2)
    print(2) - first print
    mystery(2 + 1 = 3)
      print(3) - first print
      mystery(3 + 1 = 4)
        print(4) - first print
        print(4) - second print
      print(3) - second print
    print(2) - second print
  print(1) - second print

每次调用函数的第一次打印,显示正在计数的数字。但是一旦你点击4,函数就不再调用自己(这是“终止条件”),然后调用树开始展开。在n=4的情况下,它会跳过再次调用
summary()
并打印。然后该函数返回到上一个调用(它是
神秘(3)
,打印,然后退出)。这将一直持续,直到所有内容都展开并且程序退出。

由于打印位置(n),它发生在for if语句之后。此外,由于它是该函数的一部分,因此每次调用该函数时都会打印它。但是,由于您已经调用了该函数四次,它将命中该print语句四次。我感谢它打印和降序的原因,因为每次调用该方法时,它都会添加到全局执行上下文的堆栈中。用一个简单的图表最容易理解堆栈,可以在递归函数部分找到它。堆栈遵循后进先出规则,因此,当这四个方法从堆栈中弹出时,您的打印将以最新的定义开始,并继续以相反的顺序从堆栈中弹出内容。

因为递归调用返回后有第二条打印语句。当函数“终止”(
神秘
)时,它返回到以前的函数,并进行第二次打印。由于条件
4<4
为false,它跳过
if
部分。然后,由于之前对神秘函数的每次调用都是在
if
条件下完成的,因此它会在下一行(即最后一行
print(n)
)中继续程序流程,打印从
3
1
的所有值。我以为我以前见过这个问题…:(10k+)
mystery(1)
  print(1) - first print
  mystery(1 + 1 = 2)
    print(2) - first print
    mystery(2 + 1 = 3)
      print(3) - first print
      mystery(3 + 1 = 4)
        print(4) - first print
        print(4) - second print
      print(3) - second print
    print(2) - second print
  print(1) - second print