编者:李国帅
时间:2006-9-27
背景原因:
算是朝花夕拾了,可以帮助理解函数调用约定。
问题描述及期望效果:
以下这些语句的输出结果是多少呢?
所需资源:
Vc
Microsoft Visual C++(简称Visual C++、MSVC、VS或VC)是微软公司的免费C++开发工具,具有集成开发环境,可提供编辑C语言,C++以及C++/CLI等编程语言。
测试结果:
经过测试,编译环境是在vc71中的结果如下
参考网友论述
C 约定规定参数传递顺序是从右到左,即最右边的参数最先压栈,由调用者恢复堆栈指针
PASCAL约定和C约定正好相反,它规定参数是从左向右传递,由被调用者恢复堆栈。
Win16采用了PASCAL约定, 因为PASCAL约定产生的代码量要小。
当不知道参数的个数时,C约定特别有用。如在函数wsprintf () 中, wsprintf预先并不知道要传递几个参数,所以它不知道如何恢复堆栈。
STDCALL是C约定和PASCAL约定的混合体,它规定参数的传递是从右到左,恢复堆栈的工作交由被调用者。
Win32只用STDCALL约定,但除了一个特例,即:wsprintf。
C的调用约定是 cdecl,而且由于cdecl是从右向左入栈,所以printf可以接受变长参数而wsprintf为cdecl调用,也是因为变长参数的问题
分析:
----我也想到可能和压栈有关,
0进栈,i++
1进栈,i++
2进栈,i++
然后从顶部输出2,1,0。
编译环境是在vc71中,
printf("%d,%d,%d\n",i++,i++,i++);//2,1,0
printf("%d,%d,%d\n",++i,++i,++i); //6,6,6
如果是压栈的话,第二句怎么解释?为什么不是4,5,6呢?
不知道这样理解对不对,在给printf准备参数的时候,因为++i的关系i已经被已经变成了6,被放在arg0,arg1,arg2,所以看到的就是6,6,6