typedef的详解
合集下载
相关主题
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
• struct {int x; int y;} var_1; // 定义了变量var_1 • struct {int x; int y;} array_1 [10]; // 定义了数组array_1 • struct {struct{int x; int y;} part1; int part2;} cplx;
上面的代码包含了两个结构体变量:point_a和point_b,它们的数据类 型相同,都是struct {int x; int y;}类型。这种说法可能有点别扭,习惯上 说point_a和point_b都是结构体类型,为什么偏偏要说是struct {int x; int y;}类型呢?因为这种说法更加精确。比如在第一个例子中,对于 “unsigned int a, b;”这条语句,我们可以说a和b都是整数类型,但更 精确地说,它们应该是unsigned int类型。 既然struct {int x; int y;}是一种自定义的复杂数据类型,那么如果我们要 定义多个struct {int x; int y;}类型的变量,应该如何编写代码呢?其实很 简单,就当struct {int x; int y;}是一个简单数据类型就可以了:
补充3、typedef void (*fun)(void); 详解
typedef void (*fun)(void); 首先请看void (*fun)(void) 这里定义了一个函数指针fun,fun指向 有一个参数为void,返回值为void的函数。 接着再看typedef void (*fun)(void); typedef 的作用是定义一种类型,例如想上面的那样定 义的话,就定义了fun这种类型,而fun这种类型的约束条件就是,要指向一个参数为void, 并且返回值为void的函数的类型。 #include <iostream> using namespace std; typedef void (*fun)( void ) ; void Fun1( void ) { cout<<"Fun1 Run\n"; } void Fun2( void ) { cout<<"Fun2 Run\n"; } int main( ) { fun p; p=Fun1; //两者类型匹配。 p(); // p=Fun2; (*p)();//这两种p的表示方法是等价的 return 0; }
#include <iostream> using namespace std; #define f(x) x*x int main() { int a=6,b=2,c; c=f(a)/f(b); //被解释为 被解释为c=a*a/b*b 即6*6/2*2=36 被解释为 cout<<c<<"\n"; return 0; }
typedef的专题总结
小洪
用法一:为现有数据类型定义同义词 typedef 使用最多的地方是创建易于记忆的类型 名,用它来归档程序员的意图。 例如: typedef int size; 此声明定义了一个 int 的同义字,名字为 size。注 意 typedef 并不创建新的类型。它仅仅为现有类型 添加一个同义字。你可以在任何需要 int 的上下文 中使用 size: void measure(size * psz);
Fra Baidu bibliotek
补充1:链表的三种定义结构体
第一种: struct { int num ; char name[8]; char sex; double score[2]; }stu1; //方法一 只能在定义结构体时用一次,以 后再也无法定义此结构体变量,缺乏灵活性。
第二种: struct student { int num ; char name[8]; char sex; double score[2]; }stu1; //方法二 此处定义结构体student时,顺便定义了结 构体变量stu1 。 第三种: typedef struct student { int num ; char name[8]; char sex; double score[2]; }stu; //方法三 注意:此处并非结构体变量,而是结构体类 型student和stu
补充2:定义类的类型
类是面向对象程序设计语言中引入的一种新的数据 类型,既然是数据类型,就可以使用C++ typedef对 其进行定义:
• • • • • • typedef class { private: int a; public: int b; } MyClass;
其实这和定义结构体类型非常相似,不过很少有人 这么使用。
定义结构体类型
结构体是一种较为常见的数据类型,在C/C++程序设计中使用的非 常广泛。下面的代码就是结构体类型的一个应用: #include <iostream> using namespace std; int main (int argc, char *argv[]) { struct { int x; int y; }point_a, point_b; point_a.x = 10; point_a.y = 10; point_b.x = 0; point_b.y = 0; ios::sync_with_stdio(); cout << point_a.x + point_a.y << endl; cout << point_b.x + point_b.y << endl; return 0; }
显然,这种方法没有C++ typedef更加直观(在C++中,main函数第一行的 struct关键字可以省略,但在标准C中,省略该关键字会出现编译错误)。 此外,对于定义链接队列中的结点,我们可以这样实现:
• • • • • • • • • • typedef struct t_node { int Value; struct t_node *next; } Node; 当然也可以这样定义: typedef strcut t_node Node; struct t_node { int Value; Node *next; };
上面的第三行定义了一个cplx变量,它的数据类型是一个h复杂的结构 体类型,有两个成员:part1和part2。part1是struct {int x; int y;}类型的, part2是int类型的。 从上面的例子可以看出,如果在程序中需要多处定义struct {int x; int y;} 类型的变量,就必须多次输入“struct {int x; int y;}”这一类型名称,况 且,如果在结构体中有某个成员是struct {int x; int y;}类型的,还会使得 定义变得非常繁杂而且容易出错。为了输入程序的方便,同时为了增 强程序的可读性,我们可以把struct {int x; int y;}这一数据类型定义为标 识符“Point”,那么上面的程序就会变得更容易理解:
需要说明的是,我们还可以使用下面的方法来定义结构体变量:
struct t_Point { int x; int y;}; // 注意,这里最后一个分号不能省略 int main(int argc, char* argv[]) { struct t_Point a, b; // . . . return 0; }
typedef float REAL;
C++实例
(1)typedef long byte_4; 给已知数据类型long起个新名字, 叫byte_4。 (2)typedef struct tagMyStruct { int iNum; long lLength; } MyStruct; 完成两个工作,一是定义了struct tagMyStruct结构,可以用 struct tagMyStruct varName来定义变量,但要注意,使用 tagMyStruct varName来定义变量是不对的,因为struct 和 tagMyStruct合在一起才能表示一个结构类型。二是typedef 为这个新的结构起了一个名字,叫MyStruct。可以使用 MyStruct varName来定义变量。
补充4:typedef 与define的区别
• • • • • • • • • • (1)有下面两种定义pStr数据类型的方法,两者有什么不同?哪一种更好一点? typedef char *pStr; #define pStr char *; 答案与分析: 通常讲,typedef要比#define要好,特别是在有指针的场合。请看例子: typedef char *pStr1; #define pStr2 char *; pStr1 s1, s2; pStr2 s3, s4;//相当于char * s3,s4。而*的有效域只有一位,所以*只跟s3结合形成指针 在上述的变量定义中,s1、s2、s3都被定义为char *,而s4则定义成了char,不是我们 所预期的指针变量,根本原因就在于#define只是简单的字符串替换而typedef则是为一个 类型起新名字。
• typedef 有另外一个重要的用途,那就是定义机器无关的类型,例如, 你可以定义一个叫 REAL 的浮点类型,在目标机器上它可以i获得最 高的精度: • typedef long double REAL; • 在不支持 long double 的机器上,该 typedef 看起来会是下面这 样: • typedef double REAL; • 并且,在连 double 都不支持的机器上,该 typedef 看起来会是 这样:、
用法三:在链表中的应用
链表中应用 例如: typedef struct node { char name[20]; struct node *link; }stu;
用法四:代码简化和促进扩平台开发
1、代码简化 例如:typedef int (*PF) (const char *, const char *); 使用PF 类型作为函数指针的同义字,该函数有两个 const char * 类型的参数以及一个 int 类型的返回值。 2、促进扩平台开发
• • • • • • • • • • • •
typedef struct {int x; int y;} Point; Point var_1; // 定义了变量var_1 Point array_1 [10]; // 定义了数组array_1 struct {Point part1; int part2;} cplx; // 定义了复杂类型变量cplx
用法二:typedef 还可以掩饰复合类型,如指针和数组
• 1、数组 • 例如: typedef char Line[81];表示使用Line代表具有81个元素 的char类型数组。如果要生成类似的数据可以使用如下形式: Line text, secondline; 相当于char test[81];char secondline[81]; • 2、隐藏指针语法 例如: typedef char * pstr; int mystrcmp(pstr, pstr);相当于 int mystrcmp(char *,char *); • 注意:标准函数 strcmp()有两个‘const char *'类型的参数。 因此,它可能会误导人们象下面这样声明 mystrcmp(), • int mystrcmp(const pstr, const pstr); • 这是错误的,按照顺序,‘const pstr'被解释为‘char * const' (一个指向 char 的常量指针),而不是‘const char *'(指向 常量 char 的指针)。这个问题很容易解决:。 • 修改:typedef const char * cpstr; • int mystrcmp(cpstr, cpstr); // 现在是正确的 记住:不管什么时候,只要为指针声明 typedef,那么都要在最 终的 typedef 名称中加一个 const,以使得该指针本身是常量, 而不是对象
上面的代码包含了两个结构体变量:point_a和point_b,它们的数据类 型相同,都是struct {int x; int y;}类型。这种说法可能有点别扭,习惯上 说point_a和point_b都是结构体类型,为什么偏偏要说是struct {int x; int y;}类型呢?因为这种说法更加精确。比如在第一个例子中,对于 “unsigned int a, b;”这条语句,我们可以说a和b都是整数类型,但更 精确地说,它们应该是unsigned int类型。 既然struct {int x; int y;}是一种自定义的复杂数据类型,那么如果我们要 定义多个struct {int x; int y;}类型的变量,应该如何编写代码呢?其实很 简单,就当struct {int x; int y;}是一个简单数据类型就可以了:
补充3、typedef void (*fun)(void); 详解
typedef void (*fun)(void); 首先请看void (*fun)(void) 这里定义了一个函数指针fun,fun指向 有一个参数为void,返回值为void的函数。 接着再看typedef void (*fun)(void); typedef 的作用是定义一种类型,例如想上面的那样定 义的话,就定义了fun这种类型,而fun这种类型的约束条件就是,要指向一个参数为void, 并且返回值为void的函数的类型。 #include <iostream> using namespace std; typedef void (*fun)( void ) ; void Fun1( void ) { cout<<"Fun1 Run\n"; } void Fun2( void ) { cout<<"Fun2 Run\n"; } int main( ) { fun p; p=Fun1; //两者类型匹配。 p(); // p=Fun2; (*p)();//这两种p的表示方法是等价的 return 0; }
#include <iostream> using namespace std; #define f(x) x*x int main() { int a=6,b=2,c; c=f(a)/f(b); //被解释为 被解释为c=a*a/b*b 即6*6/2*2=36 被解释为 cout<<c<<"\n"; return 0; }
typedef的专题总结
小洪
用法一:为现有数据类型定义同义词 typedef 使用最多的地方是创建易于记忆的类型 名,用它来归档程序员的意图。 例如: typedef int size; 此声明定义了一个 int 的同义字,名字为 size。注 意 typedef 并不创建新的类型。它仅仅为现有类型 添加一个同义字。你可以在任何需要 int 的上下文 中使用 size: void measure(size * psz);
Fra Baidu bibliotek
补充1:链表的三种定义结构体
第一种: struct { int num ; char name[8]; char sex; double score[2]; }stu1; //方法一 只能在定义结构体时用一次,以 后再也无法定义此结构体变量,缺乏灵活性。
第二种: struct student { int num ; char name[8]; char sex; double score[2]; }stu1; //方法二 此处定义结构体student时,顺便定义了结 构体变量stu1 。 第三种: typedef struct student { int num ; char name[8]; char sex; double score[2]; }stu; //方法三 注意:此处并非结构体变量,而是结构体类 型student和stu
补充2:定义类的类型
类是面向对象程序设计语言中引入的一种新的数据 类型,既然是数据类型,就可以使用C++ typedef对 其进行定义:
• • • • • • typedef class { private: int a; public: int b; } MyClass;
其实这和定义结构体类型非常相似,不过很少有人 这么使用。
定义结构体类型
结构体是一种较为常见的数据类型,在C/C++程序设计中使用的非 常广泛。下面的代码就是结构体类型的一个应用: #include <iostream> using namespace std; int main (int argc, char *argv[]) { struct { int x; int y; }point_a, point_b; point_a.x = 10; point_a.y = 10; point_b.x = 0; point_b.y = 0; ios::sync_with_stdio(); cout << point_a.x + point_a.y << endl; cout << point_b.x + point_b.y << endl; return 0; }
显然,这种方法没有C++ typedef更加直观(在C++中,main函数第一行的 struct关键字可以省略,但在标准C中,省略该关键字会出现编译错误)。 此外,对于定义链接队列中的结点,我们可以这样实现:
• • • • • • • • • • typedef struct t_node { int Value; struct t_node *next; } Node; 当然也可以这样定义: typedef strcut t_node Node; struct t_node { int Value; Node *next; };
上面的第三行定义了一个cplx变量,它的数据类型是一个h复杂的结构 体类型,有两个成员:part1和part2。part1是struct {int x; int y;}类型的, part2是int类型的。 从上面的例子可以看出,如果在程序中需要多处定义struct {int x; int y;} 类型的变量,就必须多次输入“struct {int x; int y;}”这一类型名称,况 且,如果在结构体中有某个成员是struct {int x; int y;}类型的,还会使得 定义变得非常繁杂而且容易出错。为了输入程序的方便,同时为了增 强程序的可读性,我们可以把struct {int x; int y;}这一数据类型定义为标 识符“Point”,那么上面的程序就会变得更容易理解:
需要说明的是,我们还可以使用下面的方法来定义结构体变量:
struct t_Point { int x; int y;}; // 注意,这里最后一个分号不能省略 int main(int argc, char* argv[]) { struct t_Point a, b; // . . . return 0; }
typedef float REAL;
C++实例
(1)typedef long byte_4; 给已知数据类型long起个新名字, 叫byte_4。 (2)typedef struct tagMyStruct { int iNum; long lLength; } MyStruct; 完成两个工作,一是定义了struct tagMyStruct结构,可以用 struct tagMyStruct varName来定义变量,但要注意,使用 tagMyStruct varName来定义变量是不对的,因为struct 和 tagMyStruct合在一起才能表示一个结构类型。二是typedef 为这个新的结构起了一个名字,叫MyStruct。可以使用 MyStruct varName来定义变量。
补充4:typedef 与define的区别
• • • • • • • • • • (1)有下面两种定义pStr数据类型的方法,两者有什么不同?哪一种更好一点? typedef char *pStr; #define pStr char *; 答案与分析: 通常讲,typedef要比#define要好,特别是在有指针的场合。请看例子: typedef char *pStr1; #define pStr2 char *; pStr1 s1, s2; pStr2 s3, s4;//相当于char * s3,s4。而*的有效域只有一位,所以*只跟s3结合形成指针 在上述的变量定义中,s1、s2、s3都被定义为char *,而s4则定义成了char,不是我们 所预期的指针变量,根本原因就在于#define只是简单的字符串替换而typedef则是为一个 类型起新名字。
• typedef 有另外一个重要的用途,那就是定义机器无关的类型,例如, 你可以定义一个叫 REAL 的浮点类型,在目标机器上它可以i获得最 高的精度: • typedef long double REAL; • 在不支持 long double 的机器上,该 typedef 看起来会是下面这 样: • typedef double REAL; • 并且,在连 double 都不支持的机器上,该 typedef 看起来会是 这样:、
用法三:在链表中的应用
链表中应用 例如: typedef struct node { char name[20]; struct node *link; }stu;
用法四:代码简化和促进扩平台开发
1、代码简化 例如:typedef int (*PF) (const char *, const char *); 使用PF 类型作为函数指针的同义字,该函数有两个 const char * 类型的参数以及一个 int 类型的返回值。 2、促进扩平台开发
• • • • • • • • • • • •
typedef struct {int x; int y;} Point; Point var_1; // 定义了变量var_1 Point array_1 [10]; // 定义了数组array_1 struct {Point part1; int part2;} cplx; // 定义了复杂类型变量cplx
用法二:typedef 还可以掩饰复合类型,如指针和数组
• 1、数组 • 例如: typedef char Line[81];表示使用Line代表具有81个元素 的char类型数组。如果要生成类似的数据可以使用如下形式: Line text, secondline; 相当于char test[81];char secondline[81]; • 2、隐藏指针语法 例如: typedef char * pstr; int mystrcmp(pstr, pstr);相当于 int mystrcmp(char *,char *); • 注意:标准函数 strcmp()有两个‘const char *'类型的参数。 因此,它可能会误导人们象下面这样声明 mystrcmp(), • int mystrcmp(const pstr, const pstr); • 这是错误的,按照顺序,‘const pstr'被解释为‘char * const' (一个指向 char 的常量指针),而不是‘const char *'(指向 常量 char 的指针)。这个问题很容易解决:。 • 修改:typedef const char * cpstr; • int mystrcmp(cpstr, cpstr); // 现在是正确的 记住:不管什么时候,只要为指针声明 typedef,那么都要在最 终的 typedef 名称中加一个 const,以使得该指针本身是常量, 而不是对象