推广 热搜: csgo  vue  angelababy  2023  gps  新车  htc  落地  app  p2p 

用C语言计算n的阶乘等于1,n大于呢?

   2023-06-06 网络整理佚名1200
核心提示:语言中,什么是递归函数我们已经知道,递归最重要的就是“基础条件”了,我们先把阶乘的基础条件写好:在我之前的文章《c语言入门5,一文彻底弄懂函数的形参和实参,再也不晕了》也用到了“栈帧”的概念。计算机硬件能做的所有事情就是数据存取、运算、测试和分支、循环(或递归),在计算机上运行的高级语言写的程序当然也不可能做到更多的事情,虽然高级语言有丰富的语法特性,但也只是为做这些事情提供一些方便。

不知道大家学C语言最难的是什么。 反正我初学C语言的时候,觉得最难的就是“递归”,比指针更难理解(C语言中的指针,很多人认为很难理解)。

那么什么是“递归”呢? 有一天翻字典的时候,看到字典是这样解释一个词的:

惊人:形容惊人的形容词。

这要么是恶搞,要么是开玩笑。 但是,数学中确实有很多概念是自己定义的。 比如:n的阶乘等于n乘以n-1的阶乘,0的阶乘等于1。乍一看好像没有说清楚什么是阶乘,但是这样的描述是足以让人们知道如何计算阶乘。 例如计算 4 的阶乘:

4! = 4 x 3! 
= 4 x 3 x 2! 
= 4 x 3 x 2 x 1! 
= 4 x 3 x 2 x 1 x 0! 
= 4 x 3 x 2 x 1 x 1 
= 24

什么是阶乘不需要研究,只需要根据定义计算即可。 当然,这个定义必须有一个“基本条件”。 比如阶乘的“基本条件”是0! = 1. 如果没有“基本条件”,阶乘只会无限向下推,没有尽头。

C语言中的递归函数是什么

说了半天阶乘,为“递归”做铺垫。 如果一个概念需要使用它自己,我们称它的定义为递归的。 很明显,递归函数必须调用自己的函数,所以有点假,我们来看例子,下面用C语言计算n的阶乘。 我们已经知道递归最重要的是“基本条件”。 先写下阶乘的基本条件:

int factorial(int n)
{
 if(0 == n)
 return 1;
}

上面代码实现了0的阶乘等于1,如果n大于0怎么办? 根据阶乘的定义,应该是nx(n-1),代码实现为:

int factorial(int n)
{
 if(0 == n)
 return 1;
 else
 return n*factorial(n-1);
}

这就实现了用C语言计算n的阶乘。 该函数调用自身,因此它是一个递归函数。 其实不仅是直接调用自己,间接调用自己也是递归函数。 比如A调用函数B,函数B调用A,那么A也是递归函数。

那么,递归函数是如何执行的呢?

为了方便解释,我们在函数的else部分添加了几个局部变量

int factorial(int n)
{
 if (n == 0)
 return 1;
 else {
 int recurse = factorial(n-1);
 int result = n * recurse;
 return result;
 }
}

这里以(3)为例,调用用实线箭头表示,返回用虚线箭头表示,右边的方框表示调用和返回过程中各函数调用局部变量的变化.

我们看一下图中右边代表存储空间的方框的变化过程。 随着函数调用的深入,一端的存储空间逐渐变大,然后随着函数逐层退出,这一端的存储空间逐渐变小。 这是一个具有特定属性的数据结构。 它的特点是只能在一端增长或缩短,每次访问参数和局部变量时,只能访问这一端的单元,不能访问内部单元。 例如,当(2)的存储空间在末尾时,只能访问它的参数和局部变量,而不能访问(3)和main()的参数和局部变量。

这种性质的数据结构称为栈或堆栈(Stack)。 每次函数调用的参数和局部变量的存储空间(图中的一个小方框)称为栈帧(Stack frame)。 系统为每个程序的运行预留了一个栈空间。 当一个函数被调用时,在这个栈空间中分配一个栈帧,当函数返回时,释放栈帧。

在我之前的文章《C语言入门5,一篇彻底搞懂函数形参和实参,再也不晕了》中也用到了“栈帧”的概念。

可见,用C语言写一个递归函数,最重要的是定义好“基本条件”,否则函数将永远被调用,直到系统资源耗尽,程序崩溃。 递归和循环是等价的,循环能做的事递归也能做,反之亦然。 其实有些编程语言(比如某些LISP)只有递归没有循环。

计算机硬件所能做的只是数据访问、计算、测试和分支、循环(或递归),用高级语言编写的程序运行在计算机上当然不可能做更多的事情,虽然高级语言丰富。 语法特征,但只是为做这些事情提供一些便利。 那么,为什么计算机要这样设计呢? 为什么您认为计算机需要具备这些功能,而不是更多或更少? 这些都归功于早期的计算机科学家,比如艾伦,在计算机尚未诞生的时代,他从数学理论为计算机设计指明了方向。

欢迎在评论区一起讨论和提问。 文章均为手写原创,每天用最浅显的方式介绍C语言。 如果喜欢我的文章,请关注。 您可以看到最新的更新和以前的文章。 本文部分内容涉及linux C编程一站式学习。

 
反对 0举报 0 收藏 0 打赏 0评论 0
 
更多>同类资讯
推荐图文
推荐资讯
点击排行
网站首页  |  关于我们  |  联系方式  |  使用协议  |  版权隐私  |  网站地图  |  排名推广  |  广告服务  |  积分换礼  |  网站留言  |  RSS订阅  |  违规举报
Powered By DESTOON