马上注册,结交更多好友,享用更多功能^_^
您需要 登录 才可以下载或查看,没有账号?立即注册
x
测试程序:
#include <stdio.h>
int main(void)
{
printf("%f\n", 0);
printf("%f\n", (float)123);
printf("%f\n", 123.0);
return 0;
}
=========== 大家先猜测一下输出结果,然后看下边 --------------------------
VC6中反汇编查看一下:7: printf("%f\n", 123);
00401028 push 7Bh // 这时,123当做int型
0040102A push offset string "%f\n" (0042601c)
0040102F call printf (00401090)
00401034 add esp,8
8: printf("%f\n", (float)123);
00401037 push 405EC000h
0040103C push 0 // 这时,123被转换为float型
0040103E push offset string "%f\n" (0042601c)
00401043 call printf (00401090)
00401048 add esp,0Ch
9: printf("%f\n", 123.0);
0040104B push 405EC000h
00401050 push 0
00401052 push offset string "%f\n" (0042601c)
00401057 call printf (00401090)
0040105C add esp,0Ch
根据堆栈,稍稍修改一下,测试:
#include <stdio.h>
int main(void)
{
_asm push 405EC000H; // 这里模拟一个123.0的输出
printf("%f\n", 0);
_asm pop eax; // 这里 只是为了平衡堆栈,不用管
printf("%f\n", (float)123);
printf("%f\n", 123.0);
return 0;
}
VC6结果:
7: _asm push 405EC000H;
00401028 push 405EC000h
8: printf("%f\n", 0);
0040102D push 0
0040102F push offset string "%f\n" (0042601c)
00401034 call printf (00401090)
00401039 add esp,8
9: _asm pop eax;
0040103C pop eax
10: printf("%f\n", (float)123);
0040103D push 405EC000h
00401042 push 0
00401044 push offset string "%f\n" (0042601c)
00401049 call printf (00401090)
0040104E add esp,0Ch
11: printf("%f\n", 123.0);
0040104B push 405EC000h
00401050 push 0
00401052 push offset string "%f\n" (0042601c)
00401057 call printf (00401090)
0040105C add esp,0Ch
小结:printf函数的格式输出符没有类型转换的功能,只能显式的类型转换。
例如printf("%f", (double)123);
如果你认为它可以自动类型转换,就会出现意想不到的结果。
例如printf("%f", 123);这个时候,%f会要求系统从栈中取8个字节数据进行解析,可惜啊···我们的123不够,所以取出来的数···如果VC-Debug模式下貌似是edi的值,其他的···大家自己研究一下,还有那个%f对应的数据表示的如何解析的?大家可以网上查一下浮点类型在内存中存储形式。
|