seegongsik
我的单词本
编程

调用自己的函数:递归

我们说过,函数会调用别的函数(第9课)。 那么,要是一个函数 调用它自己呢? 就像两面镜子面对面立着, 里面会不断出现同样的东西。

01

调用自己的函数

第9课里,函数把活儿打包、起了名字。
在它里面,还能调用别的函数。
递归再往前一步:
函数会再次调用它自己。
就像镜中之镜,同样的东西又多出一层。

深度 0

点一下试试。每点一次,里面就多出一层一样的框。

很神奇,但也有点吓人。
这样一直调用自己,
岂不是永远停不下来?
没错。所以递归一定需要一样东西。

02

得有个停下的地方

两面镜子真的会无止境地深进去,
可电脑做不到「永远」。
所以我们定一条规则:
「当那一块足够小时,就在那里停下。」
没有这条停止规则,它就会一直转下去,直到崩溃。

3

打开停止规则,它就在 3、2、1 停住。关掉,它就无止境地往下掉,直到崩溃。

把这个停下的地方想成「地板」就好懂了。
碰到地板之前,它一直调用自己;
碰到地板,就不再调用。
那么,怎么拆,就是关键了。

03

同一个问题的更小版本

递归真正的诀窍是这个。
把大问题看成「一步 + 同样但更小的问题」。
整段楼梯 = 一级 + 剩下的楼梯。
「剩下的」也是同一个问题,只是小了一级。
越缩越小,缩到 0 级就结束。

剩下的台阶 5

一级一级地剥掉试试。剩下的每次都是「一样但更小」的问题。

原本难的问题,忽然就变简单了。
你不必一次解决全部。
只处理「一级」,剩下的再交回给同一个函数就行。
那么,交出去的活儿,是怎么回来的呢?

04

下去,再回来

递归朝两个方向走。
先一路下到地板(调用自己,再调用自己)。
碰到地板,再倒着回来,
每一层都加上自己那一份。
就像把盘子叠起来,再从最上面一个个收走。

sum(3)
正在下去

一步步点试试。把 1+2+3 一路下到地板,再回来汇成 6。

这个「下去再回来」就是递归的心脏。
下去时把问题拆开,
回来时把答案合起来。
堆起来的活儿,从地板开始一件件解开。

05

循环的兄弟,以及更远处

递归和循环(第7课)是兄弟。
两者都「把同一件事做很多次」,但
循环是把它们横着一字排开,
递归则是一层层往里钻。
像文件夹里的文件夹,枝上又长枝,这种事最适合递归。

深度 1

点一下,枝就再分叉。同一条规则,自己画出一整棵树。

那个被打包、起了名字的函数(第9课),
如今连它自己都能调用了。
拆小、在地板停下、再收拢。
这一个想法,能解开文件夹、评论里的评论,甚至走迷宫。
下一课,我们去学怎么把好几个值成对地装起来。

一句话总结递归就是函数调用它自己。它把大问题拆成「同一个问题的更小版本」,碰到停止点后,再一路返回,把答案收拢起来。
编程
如果有帮助,请支持我们