当前位置:   article > 正文

C语言自定义数据类型详解_c 语言定义新类型

c 语言定义新类型


前言

在现实中,我们有很多的东西不能单纯用整型或者浮点型来表示,所以这里就需要自定义类型来补充这部分内容。这篇文章能帮助你更好的了解C语言的自定义类型。


一、结构体类型

结构体是C语言中非常重要的一个自定义类型,很多时候都需要用到它。

  • 什么是结构体

它的关键字是 struct,下面我就声明一个结构体

  1. struct Person
  2. {
  3. char name[12];
  4. int age;
  5. char sex[5];
  6. }

 这就是一个人的结构体,它有姓名、年龄、性别等三个成员。

同时,结构体还可以嵌套,就是一个结构体里面可以包含其他结构体类型的成员。

  • 结构体的内存对齐

那么结构体的大小该如何计算呢?

首先我们需要掌握结构体的内存对齐规则。

  1. 第一个成员在与结构体变量便宜量为0的地址处
  2. 其他成员变量要对齐到某个数字(对齐数)的整数倍的地址处。(对齐数=编译器默认的对齐数和该成员大小的较小值)
  3. 结构体总大小为最大对齐数的整数倍
  1. struct s
  2. {
  3. char n;
  4. int k;
  5. double m;
  6. }

这个结构体的大小就为: 1 + 3(内存对齐浪费的空间)+ 4 +8 = 16

  • 为什么要有内存对齐呢?
  1. 不是所有的平台都能访问任意地址上的任意数据的,某些平台只能在某些地址处取某些特定类型的数据。
  2. 数据结构(尤其是栈)应该尽可能在自然边界上对齐。

在设计结构体时,如果要尽量节省空间,可以让空间小的成员尽量集中在一起。

#pragma pack() 可以修改结构体的对齐数

  • 结构体传参
  1. struct S
  2. {
  3. int data;
  4. int num;
  5. };
  6. struct S s = {1,100};
  7. //结构体传参
  8. void print1(struct S s)
  9. {
  10. printf("%d",s.num);
  11. }
  12. //结构体地址传参
  13. void print2(struct S* s)
  14. {
  15. printf("%d",s->num);
  16. }

二、位段

  • 什么是位段

位段的声明和结构体类似,有两个不同:

1.位段成员必须是int、unsigned int、signed int。

2.位段成员的后面有一个冒号和一个数字。

如:

  1. struct S
  2. {
  3. int a:2;
  4. int b:4;
  5. int c:8;
  6. };

 这里的数字就代表成员占了多少个bit位,并且位段的空间是按照需要以4个字节(int)或者1个字节(char)来开辟的。在vs上面S的大小就为4个字节

三、枚举类型

关键字enum

把所有可能的值列举出来

如:

  1. enum sex
  2. {
  3. man;
  4. woman;
  5. }
  6. enum sex a = man;
  7. enum sex b = woman;

 枚举的成员都是有值的,默认从0开,也可以手动赋值。

  •  枚举的优势

1.增加了代码的可读性和可维护性

2.和#define定义的标识符相比,枚举有类型检查,更加严谨

3.防止了命名污染

4.使用方便,可以一次定义多个常量

四、联合体类型

关键字union

它也是可以包含一系列的成员,但不同的是他们公用一个空间,从一个起始地址开始。

所以联合体的大小最少也是最大成员的大小。

  1. union un
  2. {
  3. char c;
  4. int i;
  5. }
  6. union un c;

 这里un的大小为4;

当最大成员的大小不是最大对齐数的整数倍时,就要对齐到最大对齐数的整数倍。

下面举一个结构体的使用示例:

判断大小端

  1. union
  2. {
  3. char c;
  4. int i;
  5. }u;
  6. u.i=1;
  7. return u.c;

这里如果 返回的是1则为小端存储,为0则是大端。


总结

自定义类型就讲到这里,希望你能够从中学到知识。

本文内容由网友自发贡献,转载请注明出处:【wpsshop博客】
推荐阅读
相关标签
  

闽ICP备14008679号