你上面的那个函数要求的返回值是long
公司主营业务:成都网站制作、网站建设、移动网站开发等业务。帮助企业客户真正实现互联网宣传,提高企业的竞争能力。创新互联建站是一支青春激扬、勤奋敬业、活力青春激扬、勤奋敬业、活力澎湃、和谐高效的团队。公司秉承以“开放、自由、严谨、自律”为核心的企业文化,感谢他们对我们的高要求,感谢他们从不同领域给我们带来的挑战,让我们激情的团队有机会用头脑与智慧不断的给客户带来惊喜。创新互联建站推出东湖免费做网站回馈大家。
int长整型的,但是你在n3时return的根本就不是这种类型的return
(*p)(n-1)+(*p)(n-3)这样的用法是绝对错误的,你没定义p是什么样的指针,而且将n+1和n-3强制转换为指针类型,再做加法,这是完全不对的(你可以去看看指针方面的知识)至于写成递归很简单啊:
long
int
f(int
n)
{
if(n3)
return
f(n+1)+f(n-3)
;
else
return
n;
}
通过分析这个代码,建立了如图的树。
1、当进去A时,num = 1;
2、接着往左进去B,num = 2;
3、往B左边及右边因为是NULL直接返回2处,再返回到1处;
4、接着往A右边C,此时num=3,这里把返回值C压入寄存器RAX,代码返回到A,但是最上层A处没有接收返回值,此时A退出,main函数从RAX取出返回值赋值给变量a。
这就是整个调用过程,这里返回值并不是最上层的返回值,是C的返回值,之所以能得到这个值是这个程序没有同步其它地方使用了RAX寄存器,它的值没有被修改。
int hehe(int n) {
if(n=1) return 1;
return n * hehe(n-1);
}
我们一点一点来看:
首先 n = 0 传入,if条件满足 返回 hehe(0) = 1
在传入 n = 1, if条件还是满足 返回 hehe(1) = 1
我们传入参数 n = 2, if 条件不满足 hehe(2) = 2 * hehe( 2 - 1 )= 2 * 1
在我们传入 n =3 , if条件不满足 hehe(3) = 3 * hehe(2) == 3 * 2 * 1
你继续这个步骤 ,对任何正整数n
hehe(n) = n * hehe(n-1) = n * (n-1) * ......* 1
明白了吗?!
你的说法是有问题的。
通常说,通过指针作为函数的参数,可以再被调函数中,修改实际参数所指向的变量的值,也就是把改变传递给主调函数。
但是,请看清楚上面的说法,“通过指针作为函数的参数,可以再被调函数中,修改实际参数所指向的变量的值”。是修改实际参数所指向的变量的值,而不是修改实际参数本身。
你的代码里面是要修改实际参数本身,而不是修改实际参数所指向变量。
要完成这个功能,你就需要指向指针的指针了
return; 返回调用点;
非递归,返回调用他的那个函数,调用他的那个地方;
递归调用,返回自己调用自己的地方,或者第一次调用他的地方,这个只有分析代码才知道具体情况。
无返回值函数,相当于,BASIC 的子程序,pascal 的过程,返回调用语句处,以便执行下一条语句,实际返回点是下一条指令,然后可能还要,再执行些,调用后的扫尾的工作,才来到下一步执行。
有返回值函数,返回使用函数值的地方。
不管哪一种,都是返回调用处,继续向下执行。
函数调用,首先要执行计算参数的任务,然后执行参数传递的工作,然后才轮到调用函数。
函数调用前,可能还要保存现场,具体就是寄存器压栈保存,防止函数调用时,现场被破坏
调用完成,要恢复现场,恢复寄存器的值,具体就是从堆栈中,弹出保存的寄存器数据值。
递归函数,一般包含:
1)退出条件,适当条件下函数退出递归。
2)递归部分(自调用,并适当更新,执行条件,函数参数,全局变量等)
3)执行部分,如打印节点信息等。
看递归代码,
1)首先,看何时退出递归(程序不再执行自调用)
2)看递归执行顺序
3)看执行代码,干了什么。和递归部分的执行的先后顺序。
4)有些递归函数,没有独立的执行部分,只有一些表达式,看他先后执行那些表达式。
5)有些递归函数,只看函数本身看不出是递归函数,因为这个函数,会调用别的函数,别的函数又会再回头调用该函数本身。
这就要查看,函数调用链,里面是否调用了自己。
PS:
不管是否递归,函数总是要干点什么的(函数的功能)。
所以,看递归函数,不能光看函数,自己调用自己的,递归部分;
还要看,非递归部分干了什么,这个部分,才是递归实际干的事情;
递归不过是一种重复而已,通过递归部分反复调用自己;
从而重复执行非递归部分,完成递归函数的功能。
C,C++ :return 语句有两个功能
1)返回调用处,程序执行下一步。
2)返回执行的结果
1)这个功能,返回的函数调用的位置,执行下步的程序。
在表达式中,函数调用会得到一个结果,程序解析表达式的时候遇到函数,会调用函数
代码执行,会因此跳到函数内部,开始执行函数内部的程序,执行完毕;
会得到一个结果,这个结果就是函数的返回值,也叫函数值,
这时函数调用就结束了,程序返回继续解析表达式,并用函数返回值代替函数,继续解析(计 算)表达式。
1) 如果表达式比较复杂的话;如果表达式解析没有完成,函数返回解析表达式的断点处,
如果完成了,执行下一条语句,
2)如果表达式比较简单,函数返回后,会执行下一条语句。
单独的一条函数调用,称为函数调用表达式。
所以,C 几乎一切都是表达式。
任何表达式,加上分号,就是一条语句。
所以 单独的函数调用加上分号,构成一条单独的函数调用表达式语句,就是函数调用语句。
函数调用语句,执行完成后返回调用点,执行逻辑上的下一条语句。
总结:
函数返回
1)返回值:函数返回值,放在特定的寄存器中(
X86,WINDOWS WIN32 VC eax---char,int 指针; edx:eax---long long,__int64;协处理器的浮点堆栈寄存器 float,double,long double :ST(0) ),如果返回值的类型,比较长,会使用一个全局变量(static???)存放返回值,并把该全局变量的指针,放在特定的寄存器中(X86,WINDOWS WIN32 VC:
eax)。
2)返回位置:函数结束,程序返回调用点。继续执行。
注意:由于函数可以用在表达式中,所以函数实际返回,解析表达式的断点处,继续解析表达式。
函数调用本身,就是一个表达式,称为函数调用表达式。