C语言学习随记:#define和typedef
#define在C语言中是预处理命令,在C语言的预处理阶段进行处理(代码编译之前进行处理)。
宏定义在 C 语言源程序中允许用一个标识符来表示一个字符串,称为“宏/宏体”
,被定义为“宏”的标识符称为“宏名”。在编译预处理时,对程序中所有出现的宏名,都用宏定义中的字符串去代换,这称为“宏替换”或“宏展开”。 *宏定义是由源程序中的宏定义命令完成的,宏代换是由预处理程序自动完成的。
在C语言中宏定义分为两种:1、无参数宏。2、有参数宏。
1、无参数宏定义。
#include <stdio.h>
#define pi 3.14
int main() {
float s = 0,r=2;
s = pi * r * r;
printf("%.2f",s);
return 0;
}
上述代码中,pi没有在main中定义也没有赋值,但是却可以当作3.14来用,这就是宏定义了pi,以后在此程序中看到啦pi都可以当作3。14来用。
2、带参数宏定义
#include <stdio.h>
#define fun(a) a*a
int main() {
int x = 2, result = 0;
result = fun(x);
printf("%d\n",result);
return 0;
}
输出结果为4
在这里fun相当于被a*a替换了。
当然值得注意的是,如果直接让fun参与运算会发生什么。例如:
#include <stdio.h>
#define fun(a) a*a
int main() {
int x = 2, result = 0;
result = fun(x);
printf("fun(x):%d\n",result);
result = 4 / fun(x);
printf("4 / fun(x):%d\n",result);
return 0;
}
运算结果:
我们发现如若第二种情况,4/fun(x)我们预测的结果应该是4/4=1,但为什么结果是4;
其实宏定义只是单纯的把我们定义的内容替换掉,并没有进行优先级考虑。我们想要得到结果1,就要在宏定义中加上括号,例如下面这样宏定义:
#include <stdio.h>
#define fun(a) (a*a)
int main() {
int x = 2, result = 0;
result = fun(x);
printf("fun(x):%d\n",result);
result = 4 / fun(x);
printf("4 / fun(x):%d\n",result);
return 0;
}
输出结果:
看,这样就完成了我们想要的的结果。
接下来再看typedef与#define的区别:
#define dps struct s* //定义dps为一个指向结构体s的指针
typedef struct s* tps; //定义tps为一个指向结构体s的指针
上面两种情况都是定义一个指向结构体s的指针。但是那个更好呢?
typdef更好,请看下面的例子:
dps p1, p2;
tps p3, p4;
第一行相当于:struct s* p1, p2;即定义了一个p1指针指向结构体,而p2为一个实际的结构体;
而第二行相当于直接定义了两个指向结构体的p3和p4指针。
#define是在编译预处理阶段进行处理,且遇到宏名只是做简单的替换,也不会进行正确性检查。
而typedef如同定义变量方法一样声明一种类型。