前一段时间,网上看到一个程序员在唠叨,说不明白为什么很多程序员都喜欢用for(;;)来做为死循环,又说while(1){}有多好。其实从差别上来说for(;;)与while(1)确实不大,对于应用层面的人来说是一样的,但是一般来说for(;;)会比while(1)好一些的,习惯而言,很多人就用for(;;)了。
为什么说For(;;) 比 while(1)要好呢?
下面我们透过汇编举例说明:
这是一个c语言的实例源码
#include <stdio.h>
/*
* for(;;)
*/
void for_test()
{
for(;;);
}
/*
* while(1)
*/
void while_test()
{
while(1){
}
}
void main()
{
for_test();
}
反汇编后:
1: #include <stdio.h>
2:
3: /*
4: * for(;;)
5: */
6: void for_test()
7: {
00401030 push ebp //进入for_test 前先压栈保存原基地址指针ebp, esp+4
00401031 mov ebp,esp //把基地址指针重新定位到堆栈指针
00401033 sub esp,40h // esp - 0x40h,
00401036 push ebx //保存基地址 esp + 4
00401037 push esi //保存源索引地址esp + 4
00401038 push edi //保存目标索引地址esp + 4
00401039 lea edi,[ebp-40h] //回到栈顶
0040103C mov ecx,10h //ecx 设置 10h,在下面将作为循环次数
00401041 mov eax,0CCCCCCCCh //eax 置值0CCCCCCCC
00401046 rep stos dword ptr [edi] //填充值到edi指向的内存
8: for(;;);
00401048 jmp for_test+18h (00401048)//重点在这里,进入死循环
0040104A int 3
0040104B int 3
0040104C int 3
0040104D int 3
0040104E int 3
0040104F int 3
9: }
10:
11: /*
12: * while(1)
13: */
14: void while_test()
15: {
00401050 push ebp
00401051 mov ebp,esp
00401053 sub esp,40h
00401056 push ebx
00401057 push esi
00401058 push edi
00401059 lea edi,[ebp-40h]
0040105C mov ecx,10h
00401061 mov eax,0CCCCCCCCh
00401066 rep stos dword ptr [edi]
//上面那段反汇编同for_test
16: while(1){
00401068 mov eax,1 //eax赋值1
0040106D test eax,eax //测试eax,eax是否一样
0040106F je while_test+23h (00401073)
17: }
00401071 jmp while_test+18h (00401068)
//在这里我们可以看到,while(1)需要比for(;;)多存在些判断
18: }
00401073 pop edi
00401074 pop esi
00401075 pop ebx
00401076 mov esp,ebp
00401078 pop ebp
00401079 ret
19:
20:
21: void main()
22: {
00401090 push ebp
00401091 mov ebp,esp
00401093 sub esp,40h
00401096 push ebx
00401097 push esi
00401098 push edi
00401099 lea edi,[ebp-40h]
0040109C mov ecx,10h
004010A1 mov eax,0CCCCCCCCh
004010A6 rep stos dword ptr [edi]
23: for_test();
004010A8 call @ILT+10(_for_test) (0040100f)
24:
25: }
004010AD pop edi
004010AE pop esi
004010AF pop ebx
004010B0 add esp,40h
004010B3 cmp ebp,esp
004010B5 call __chkesp (0040d470)
004010BA mov esp,ebp
004010BC pop ebp
004010BD ret
通过对比,我们发现了证据,for(;;)对比while(1)略显得效率高一点.