![](https://csdnimg.cn/release/download_crawler_static/86946873/bg7.jpg)
当主程序执行到调用子程序 A 语句时,系统保存一些必要的现场数据,跳转到子程序 A
(为了说得简单些,我这里忽略了参数传递这个过程)。
当子程序 A 执行到调用子程序 B 语句时,系统作法如上,跳转到子程序 B。
子程序 B 执行完所有语句后,跳转回子程序 A 调用子程序 B 语句的下一条语句(我这
又忽略了返回值处理)
子程序 A 执行完后,跳转回主程序调用子程序 A 语句的下一条语句
主程序执行到结束。
做个比较:我在吃饭(执行主程序)吃到一半时,某人叫我(执行子程序 A),话正说
到一半,电话又响了起来(执行子程序 B),我只要先接完电话,再和某人把话说完,最后
把饭吃完
认识递归函数
我们在高中时都学过数学归纳法,例:
求 n!
我们可以把 n!这么定义
也就是说要求 3!,我们必须先求出 2!,要求 2!,必须先求 1!,要求 1!,就必须先求
0!,而 0!=1,所以 1!=0!*1=1,再进而求 2!,3!。分别用函数表示,则如图:
我们可以观察到,除计算 0!子程序外,其他的子程序基本相似,我们可以设计这么一
个子程序:
int factorial(int i){
int res;
res=factorial(I-1)*i;
return res;
}
那么当执行主程序语句 s=factorial(3)时,就会执行 factorial(3),但在执行 factorial(3),又
会调用 factorial(2),这时大家要注意,factorial(3)和 factorial(2)虽然是同一个代码段,但在内
存中它的数据区是两份!而执行 factorial(2)时又会调用 factorial(1),执行 factorial(1)时
又会调用 factorial(0),每调用一次 factorial 函数,它就会在内存中新增一个数据区,那么
这些复制了多份的函数大家可以把它看成是多个不同名的函数来理解;
但我们这个函数有点问题,在执行 factorial(0)时,它又会调用 factorial(-1)。。。
造成死循环,也就是说,在 factorial 函数中,我们要在适当的时候保证不再调用该函数,也
就是不执行 res=factorial(I-1)*i;这条调用语句。所以函数要改成:
int factorial(int i){