1、typedef关键字的用法
typedef是C语言中的一个关健字,用于定义新的类型(或者类型的重命名)
C语言中的类型一共有两种:
一种是编译器定义的原生类型(基础数据类型,如 int、double之类的);
第二种是用户自定义类型,不是语言自带的,而是程序员自己定义的(如数组类型、结构体类型、函数类型等)。
我们今天讲的数组指针、指针数组、函数指针等都属于用户自定义类型。
有时候自定义类型太长了,用起来不方便,所以用typedef给它重命名一个简短的名字。只是类型的命名工。 所以typedef本身并不生产类型,只是负责给类型起一个好听的名字。就像农夫山泉说“我们并不生产水,我们只是大自然的搬运工”;在这里就是,我们并不生产类型,我们只是类型的命名工。
注意:typedef是给类型重命名,也就是说type得分加工出来的都市类型,而不是变量。这里要注意类型与变量的区别。类型本身并不占内存,她只是一个模具,而变量是这个类型的一个具体实例。如果用面向对象的思想来理解,则类型就是类,而变量就是对象。
2、轻松理解和应用typedef —
用最简单的话去诠释 typeder的作用,就是用于给类型取别名。但是,并没有你想象的那么简单!
如typedef int size
,那么 int 就有一个别名叫 size 了,以后 size 就和 int 这个类型是一样的用法了。
看到这里,如果你仅仅认为typedef就是把第一个参数(类型名)等同于第二个参数这么简单,那你就想的太简单了。
再来看看下面这个例子typedef char Line[81]
中 Line[81] 就是 char 的别名吗?这显然不对。它真正的含义是Line类型代表了具有 81个先素的字符数组。那么 Line t 就等同于 char t[81]。看到这里读者是否晕了?我们尝试把它放在一起看看。
typedef int size; // typedef 行
int i; //原型行
size i; // 应用行
同理: typedef char Line[81]; // typedef 行
char t[81]; // 原型行
Line t; // 应用行
再举一个函数指针的例子,如下所示。
typedef int (*fun_ptr)(int,int); // typedef 行
int (*fp) (int,int); // 原型行
fun_ptr fp ; //应用行 fp;
以上三个例子都有以下几个共同点。
首先,“typdef行”和“原型行”相比,“typdef行”仅仅多个typedef而已。就函数指针的例子来说,typedef行”和“原型行”的根本区别在于,fun_ptr是类的别名,fp是该类的变量。
其次,“原型行”和“应用行”的编译结果是一样的。就函数指针的例子来说,它们都是创建了一个类型为 int(*)(int,int)的函数指针。只是 fun_ptrp(应用行)比 int(*fp)(int.int)(原型行)这种形式更加简洁,便于书写和理解。形式越复杂,typede 的优势就越明显。
typedef 的定义应用和理解应该是一步到位的。
1、定义过程
只要我们能写出原型行,就能直接写出typedef行,因为形式上只差一个typedef。如我们写出原型:char t[81],那么加上一个typedef 就能得到我们想要的定义,当然也可以修改下类名,如 typedef char T[81]。
2、应用过程
“Tt”中,T是之前定义的类型,t是通过该类型定义的变量。
3、 理解过程
要想理解“Tt”,就要找到与之对应的“原型行”,但是“原型行”一般在程序中不会出现,所以只能先找到“typedef行”,在通过“typedef行”推导出“原型行”(推导的过程就是去掉typedef 而已)。
在“”的定义中,的typedef定义形式为typedef char T[81],因此T:就等价于 char[81];所以:
typedet char T[81];
T t;
与直接 char t[81];是完全等价的。
小结
当我们看到一个typedef定义时,如typedef int (*fun_ptr)(inr,int)
。我们的大脑里需要考虑两件事。
1、typedef 是给类型取别名,所以只要是typedef定义的东西都是类型。所以看到以上表达式就是要意识到fun_ptr是个类型。
2、要理解typedef到底定义了什么,首先去掉typedef,再将typedef定义的“类型”看成是“变量”。如将以上表达式就看成int (*X)(int,int),就能明白该表达式的目的是想定义一个函数的指针类型。
注意事项
typedef 在语法上是一个存储类的关键字(如auto,extern , static,register),而变量只能被一种存储类的关键字修饰。
如:
typedef static int a; //错误示范