C语言函数的递归和调用

  C语言中的函数可以递归调用,即:可以直接(简单递归)或间接(间接递归)地自己调自己。

  要点:

  1、C语言函数可以递归调用。

  2、可以通过直接或间接两种方式调用。目前只讨论直接递归调用。

  二、递归条件

  采用递归方法来解决问题,必须符合以下三个条件:

  1、可以把要解决的问题转化为一个新问题,而这个新的问题的解决方法仍与原来的解决方法相同,只是所处理的对象有规律地递增或递减。

  说明:解决问题的方法相同,调用函数的参数每次不同(有规律的递增或递减),如果没有规律也就不能适用递归调用。

  2、可以应用这个转化过程使问题得到解决。

  说明:使用其他的办法比较麻烦或很难解决,而使用递归的方法可以很好地解决问题。

  3、必定要有一个明确的结束递归的条件。

  说明:一定要能够在适当的地方结束递归调用。不然可能导致系统崩溃。

  三、递归实例

  例:使用递归的方法求n!

  当n>1时,求n!的问题可以转化为n*(n-1)!的新问题。

  比如n=5:

  第一部分:5*4*3*2*1 n*(n-1)!

  第二部分:4*3*2*1 (n-1)*(n-2)!

  第三部分:3*2*1 (n-2)(n-3)!

  第四部分:2*1 (n-3)(n-4)!

  第五部分:1 (n-5)! 5-5=0,得到值1,结束递归。

  源程序:

  fac(int n)

  {int t;

  if(n==1)||(n==0) return 1;

  else

  { t=n*fac(n-1);

  return t;

  }

  }

  main( )

  {int m,y;

  printf(“Enter m:”);

  scanf(“%d”,&m);

  if(m<0) printf(“Input data Error!n”);

  else

  {y=fac(m);

  printf(“n%d! =%d n”,m,y);

  }

  }

  四、递归说明

  1、当函数自己调用自己时,系统将自动把函数中当前的变量和形参暂时保留起来,在新一轮的调用过程中,系统为新调用的函数所用到的变量和形参开辟另外的存 储单元(内存空间)。每次调用函数所使用的变量在不同的内存空间。

  2、递归调用的层次越多,同名变量的占用的存储单元也就越多。一定要记住,每次函数的调用,系统都会为该函数的变量开辟新的内存空间。

  3、当本次调用的函数运行结束时,系统将释放本次调用时所占用的内存空间。程序的流程返回到上一层的调用点,同时取得当初进入该层时,函数中的变量和形参 所占用的内存空间的数据。

  4、所有递归问题都可以用非递归的方法来解决,但对于一些比较复杂的递归问题用非递归的方法往往使程序变得十分复杂难以读懂,而函数的递归调用在解决这类 问题时能使程序简洁明了有较好的可读性;但由于递归调用过程中,系统要为每一层调用中的变量开辟内存空间、要记住每一层调用后的返回点、要增加许多额外的 开销,因此函数的递归调用通常会降低程序的运行效率。

  五、程序流程

  fac(int n) /*每次调用使用不同的参数*/

  { int t; /*每次调用都会为变量t开辟不同的内存空间*/

  if(n==1)||(n==0) /*当满足这些条件返回1 */

  return 1;

  else

  { t=n*fac(n-1); /*每次程序运行到此处就会用n-1作为参数再调用一次本函数,此处是调用点*/

  return t; /*只有在上一句调用的所有过程全部结束时才运行到此处。*/

  }

  }

时间: 2024-09-05 01:37:13

C语言函数的递归和调用的相关文章

C语言函数的递归和调用实例分析

一个函数在它的函数体内调用它自身称为递归调用.这种函数称为递归函数.C语言允许函数的递归调用.在递归调用中,主调函数又是被调函数.执行递归函数将反复调用其自身,每调用一次就进入新的一层   一.基本内容: C语言中的函数可以递归调用,即:可以直接(简单递归)或间接(间接递归)地自己调自己. 要点: 1.C语言函数可以递归调用. 2.可以通过直接或间接两种方式调用.目前只讨论直接递归调用. 二.递归条件 采用递归方法来解决问题,必须符合以下三个条件: 1.可以把要解决的问题转化为一个新问题,而这个

C语言函数的递归和调用实例分析_C 语言

一.基本内容: C语言中的函数可以递归调用,即:可以直接(简单递归)或间接(间接递归)地自己调自己. 要点: 1.C语言函数可以递归调用. 2.可以通过直接或间接两种方式调用.目前只讨论直接递归调用. 二.递归条件 采用递归方法来解决问题,必须符合以下三个条件: 1.可以把要解决的问题转化为一个新问题,而这个新的问题的解决方法仍与原来的解决方法相同,只是所处理的对象有规律地递增或递减. 说明:解决问题的方法相同,调用函数的参数每次不同(有规律的递增或递减),如果没有规律也就不能适用递归调用. 2

c语言-C语言函数间用指针调用数值的问题

问题描述 C语言函数间用指针调用数值的问题 函数原型是这样的 void f(int * u): main里有这么一句 f(&x); 相当于是把变量x的地址传递给f(),没错吧,那问题来了,被赋值的是 * u还是u? 答案自然是u 我是这样想的, * u 作为一个int整体是f()的形式参数,那就将地址以int储存,那u岂不是这个地址的地址?到底哪里理解错误了? 解决方案 int *u,u是指针,他需要指向一个地址,&x,就是x的地址,int *u = &x,这个就是把x的地址,赋值

php函数的递归调用

什么是函数的递归调用?就是函数自己调用自己. php文件: <?phpfunction abc($n) { if ($n > 2) { abc(--$n); } echo '$n=' . $n . "<br />";}abc(4);?> 输出结果: $n=2 $n=2 $n=3 以上是小编为您精心准备的的内容,在的博客.问答.公众号.人物.课程等栏目也有的相关内容,欢迎继续使用右上角搜索按钮进行搜索php , 递归 , 文件 , 函数 , 结果 输出 函数

PHP 无限分类三种方式 非函数的递归调用!_php技巧

php无限分类大致有三种方式, 1.数据库通过设置父类ID来进行唯一索引,然后使用函数的递归调用实现无限分类: 2.数据库设计通过特定格式进行排列,然后使用mysql查询关键函数:concat.程序实现比较简单: 3.第三种不是太了解, 好像要使用到算法和数据结构进行排列. 今天我主要分享下第二种方式,一开始也是找了很多资料,确实比较难理解.不过最终还是给搞明白了,因此记下随笔,希望通过这篇文章能够帮助到大家. 一.数据库设计: 复制代码 代码如下: -- -- Table structure

函数指针 c语言 指针-C语言指向函数的指针的调用

问题描述 C语言指向函数的指针的调用 int *d_bubblesort(int a[]int n)//数组长度为n的冒泡降序排序{int ij;int temp;for(i=0;i {for(j=n-1;j>i;j--){if(a[j]>a[j-1]){temp=a[j-1];a[j-1]=a[j];a[j]=temp;} }}return(a);} void main(){int i;int *p;int a[10]={65412398710};int (*fun)(intint);fun

c语言-C语言库函数中 _mlock(_CONIO_LOCK);调用的却是lock()函数,这是为什么?

问题描述 C语言库函数中 _mlock(_CONIO_LOCK);调用的却是lock()函数,这是为什么? 还有语句"_munlock(_CONIO_LOCK);" 调用的是unlock() 前面的"_m"怎么没有读取? 解决方案 http://blog.csdn.net/taomeegaoke/article/details/7463262

Go语言中函数的参数传递与调用的基本方法_Golang

按值传递函数参数,是拷贝参数的实际值到函数的形式参数的方法调用.在这种情况下,参数在函数内变化对参数不会有影响. 默认情况下,Go编程语言使用调用通过值的方法来传递参数.在一般情况下,这意味着,在函数内码不能改变用来调用所述函数的参数.考虑函数swap()的定义如下. 复制代码 代码如下: /* function definition to swap the values */ func swap(int x, int y) int {    var temp int    temp = x /

在 NewLisp 实现匿名函数的递归

匿名函数在很多语言中的表现形式大概如下: (lambda (n) (* (+ n 1) (- n 1))) 只有参数列表和函数体,而没有名字.在大部分情况下没问题,但是一旦需要用到递归的话,就有点麻烦了,因为不知道如何去递归的调用一个匿名函数. 在学术界中有一些解决这个问题的办法,其中一个就是Y组合子,但是那个太繁琐,而且难以通过宏自动将一个lambda变成可递归形式,没什么好处. 根据历史经验,目前比较好的办法,就是实现一个操作符,匿名函数通过这个操作符来调用自身: (lambda (n) .