1.各种<include>之间的顺序是否可交换?
2.<>和''加之在include上有什么区别呢?
3.if...else和switch语句在汇编中是怎样执行的以及它们都属于比较吗?
4.三重指针在什么情况下才会用到?
5.当将<include>包去掉时,系统会有错吗?如果有错,那么什么时候系统会报错?
答案:
1.各种<include>之间的顺序是否可交换?
不可以, include 就是将内容copy 进去而已。 设计的原因,很多include 不能交互
试试winsock2.h windows.h 的顺序
2.<>和''加之在include上有什么区别呢?
就是搜索的路径不同
3.if...else和switch语句在汇编中是怎样执行的以及它们都属于比较吗?
前者比较后者查表
4.三重指针在什么情况下才会用到?
在要更改二维指针的地址的时候会用到
5.当将<include>包去掉时,系统会有错吗?如果有错,那么什么时候系统会报错?
不一定报错,如果用到了对应的包里面的函数或者名字才会报错
关于include的顺序:
1、 尽可能的在源文件中include 头文件,尽量不要在 头文件引用头文件;
2、如果你的头文件的类型中含有自动变量:
a.h:
typedef struct A {
B_t b;
int c;
} A_t;
那么你的a.h非引用 b.h不可;
3、如果你的头文件的类型只含 指针变量:
a.h:
typedef struct A {
B_t *b;
int c;
};
那么在a.h中就不要include b.h了,在前面加一句:
typedef struct B_t B;
就可以了;
但是这样的话你在 a.c 里面#include "b.h", 因为b.h里面也有一句: typedef struct B_t B;
会报错,同一文件同一类型不允许 typedef 两次,所以你的 a.h必须这么写:
a.h:
struct B;
typedef struct A {
struct B *b;
int c;
};
就OK了。
3,
if...else... 和 switch 的效率再研究
昨天发现了一本叫做CSAPP的书,终于找到了关于switch问题的解答。
这是一段C代码:
/* $begin switch-c */
int switch_eg(int x)
{
int result = x;
switch (x) {
case 100:
result *= 13;
break;
case 102:
result += 10;
/* Fall through */
case 103:
result += 11;
break;
case 104:
case 106:
result *= result;
break;
default:
result = 0;
}
return result;
}
/* $end switch-c */
用GCC汇编出来的代码如下:
.file "switch.c"
.version "01.01"
gcc2_compiled.:
.text
.align 4
.globl switch_eg
.type switch_eg,@function
switch_eg:
pushl %ebp
movl %esp,%ebp
movl 8(%ebp),%edx
leal -100(%edx),%eax
cmpl ,%eax
ja .L9
jmp *.L10(,%eax,4)
.p2align 4,,7
.section .rodata
.align 4
.align 4
.L10:
.long .L4
.long .L9
.long .L5
.long .L6
.long .L8
.long .L9
.long .L8
.text
.p2align 4,,7
.L4:
leal (%edx,%edx,2),%eax
leal (%edx,%eax,4),%edx
jmp .L3
.p2align 4,,7
.L5:
addl ,%edx
.L6:
addl ,%edx
jmp .L3
.p2align 4,,7
.L8:
imull %edx,%edx
jmp .L3
.p2align 4,,7
.L9:
xorl %edx,%edx
.L3:
movl %edx,%eax
movl %ebp,%esp
popl %ebp
ret
.Lfe1:
.size switch_eg,.Lfe1-switch_eg
.ident "GCC: (GNU) 2.95.3 20010315 (release)"
在上面的汇编代码中我们可以很清楚的看到switch部分被分配了一个连续的查找表,switch case中不连续的部分也被添加上了相应的条目,switch表的大小不是根据case语句的多少,而是case的最大值的最小值之间的间距。在选择相应 的分支时,会先有一个cmp子句,如果大于查找表的最大值,则跳转到default子句。而其他所有的case语句的耗时都回事O(1)。
相比于if-else结构,switch的效率绝对是要高很多的,但是switch使用查找表的方式决定了case的条件必须是一个连续的常量。而if-else则可以灵活的多。
转自: http://joehust.ycool.com/post.1692407.html