ARTICLE DETAIL

建站实战干货

来自一线的建站与推广经验沉淀,每一条都经过真实交付验证。

C语言基础:构造数据类型(自定义数据类型)

2026/8/12 18:15:09 拓冰建站 浏览量
C语言基础:构造数据类型(自定义数据类型) 结构体把多个数据类型包含基本数据类型和构造数据类型组合在一起描述一个相对复杂的事物(个体)定义结构体的语法先声明 结构体在定义结构 变量进行数据的访问声明 struct 结构体名 { 具体的属性值1; 具体的属性值2; 具体的属性值3; 具体的属性值4; 具体的属性值5; } // 有个分号不可以省略 // 只是声明 不开辟内存空间。 ​ struct Date { int year; int mon; int day; } struct Person { char name[50]; int age; int heigh; char phone[20]; struct Date date; };定义结构体变量​ struct 结构体名 变量名 ​ 开辟内存空间。 struct Person per2; ​ struct Person *point per2结构体成员的访问运算符 . 双目运算符 从左到右 1级优先级 - 双目运算符 从左到右 1级优先级 ​ 何时使用 . 或 - , 取决于 运算符的的左操作数 左操作数是变量使用. 如果是指针的话使用- 访问成员的时候如果是通过变量访问 使用. 运算符 访问成员的时候如果是通过指针访问 使用-运算符 ​ per2 是变量的情况 per2.name ; 表达式的类型是 name 的数据类型 。 当使用访问运算符访问后表达式的类型 由右操作数决定 per2 是指针的情况 per2-name ; 表达式的类型是 name 的数据类型 。 当使用访问运算符访问后表达式的类型 由右操作数决定 ​结构体的大小struct Person { char name[50]; // 50 int age; //4 float heigh; //4 char phone[20]; //20 // struct Date date; }; 口算的总大小 504420 78 byte ​ ​ printf(sizeof per is %lu\n,sizeof(struct Person )); 80byte字节对齐问题 默认 4字节对齐当结构体声明好 系统会对结构内存空间布局进行调整。 为了提高cpu 读写内存的效率。需要存储变量的地址 值 和该类型的大小 进行求余操作。如果余数为0 。则该变量储存在这个地址。如果不是地址加1后再试。2 。 找到结构体中占用空间最大的成员(基本数据类型的成员 4byte/8byte) 。 最终结构体的大小 是4的倍数或8的倍数。结构体传参值传递void fun(struct Person per) { ​ //对结构体的数据成员操作 //只能读取操作 } ​ 用的少 略势 由于是值传递所以在被调函数中需要对实参进行整体复制。 函数调用完毕后形参空间需要释放。如果结构体占用内存空间很多的话。效率就很低地址传递地址传递 内存使用效率高。 因为任意指针都是8个字节。 在被调函数中如果只需要读取数据的话加const 修饰指针就可以了。 如果需要读写的话去掉const修改。 ​ struct Date { int year; int mon; int day; }; struct Person { char name[50]; // 这个地方是结构体的声明不能给变量初值 int id; // 原因是没有内存空间 struct Date date; }; ​ void fill_per(struct Person* p) // 对结构体进行修改 { printf(input name:); scanf(%s, p-name); ​ printf(input id:); scanf(%d, p-id); ​ printf(input birth year:); scanf(%d, p-date.year); ​ printf(input birth mon:); scanf(%d, p-date.mon); ​ printf(input birth day:); scanf(%d, p-date.day); } void show_per(const struct Person* p) // 对结构体进行读取操作 { printf(name:%s id:%d y:%d m:%d d:%d\n, p-name, p-id, p-date.year, p-date.mon, p-date.day); } int main(int argc, char** argv) { struct Person per {0}; ​ // 用0 填充 结构体 清0 memset(per, 0, sizeof(per)); fill_per(per); show_per(per); ​ return 0; }结构体数组定义​ struct 结构体名 数组名[整形常量] ​ 定义 strcut Person array[10];初始化//全部清 0 struct Person array[5]{0}; ​ // 全部初始化 struct Person array2[3]{ {zhangsan,10,{2026,05,10}}, {lisi,11,{2025,03,12}}, {wangmaizi,12,{2024,01,22}}, }; // gcc 支持的初始化方式 struct Person array3[3] { [1]{zhangsan,20,{2021,10,1}}, };访问void show_pers(const struct Person arrar[],int size) { int i 0 ; for(i0;isize;i) { show_per(arrar[i]); //下标方式访问 } } int main(int argc, char **argv) { //全部清 0 struct Person array[5]{0}; ​ // 全部初始化 struct Person array2[3]{ {zhangsan,10,{2026,05,10}}, {lisi,11,{2025,03,12}}, {wangmaizi,12,{2024,01,22}}, }; // gcc 支持的初始化方式 struct Person array3[3] { [1]{zhangsan,20,{2021,10,1}}, }; ​ ​ printf(array3 name:%s y:%d m:%d d:%d\n,array3[1].name,array[1].date.year,array[1].date.mon ,array[1].date.day); ////下标方式访问 show_pers(array2,3); ​ return 0; }typedef 和struct​ ​ struct Person { char name[50]; int id; }; ​ typedef unsigned char u8; typedef int* (*PFUN)(int, int); //函数指针类型 typedef struct Person1 { char name[50]; int id; } PER; ​ // PER struct Person1 ​ int main(int argc, char** argv) { struct Person per {0}; ​ PER per2 {zhangsan, 20}; struct Person1 per3 {lisi, 10}; printf(name:%s id:%d\n, per2.name, per2.id); return 0; }共用体联合体共用体也叫联合体。和结构体的定义初始化访问元素都一样的。有一处差异开辟内存空间有差异。在结构体中每个成员都是要开辟内存空间的字节对齐问题。共用体中 开辟空间的大小是最大成员的大小。所有的成员共享一份内存。应用需要节省内存空间的情况 如果可以使用结构体或联合体作为函数参数传递的时候如果参数本身有多个选项的时候所有的选项以联合体形式给出(多选1)。可以判断大小端定义union 共用体类型名 { 数据成员1; 数据成员2; 数据成员3; ... }; // 分号不可省略 ​初始化和访问union TestAAA { int a; char b; long d; }; ​ int main(int argc, char **argv) { //清零 union TestAAA test{0}; ​ 访问 test.a 300; printf(a is %d\n,test.a); printf(b is %d\n,test.b); printf(b is %ld\n,test.d); test.d 123132300; // 会覆盖原来 test.a 中值 内存只有一份。 ​ ​ return 0; } ​大小端判断//大小端判断 union End { int ia; char cc; }; int main(int argc, char **argv) { union End end {0}; end.ia 1; printf(union size is %lu\n,sizeof(union End )); if (1 end.cc) { printf(小端\n); } else { printf(大端\n); } ​ return 0; } ​枚举 (enum)定义一个自定义的变量把变量可以取到所有的值一一列举出(或者说一个取值的范围)来。枚举值在c语言中当 整形(int)常量数据看。声明 枚举类型​ enum 枚举类型名 {枚举值1,枚举值2枚举值3,枚举值4.....} ​ 枚举值 默认从0 开始后面的只都是依次1 // MON 0 1 2 3 4 5 6 enum WEEK {MON,TUE,WED,THU,FRI,SAT,SUN}; ​ 枚举值 用户可以指定初值。 //3 4 5 6 7 8 9 enum WEEK1 {MON13,TUE1,WED1,THU1,FRI1,SAT1,SUN1};定义变量enum 枚举类型名 变量名 ​ //初始化 enum WEEK week THU; // week 1000; 枚举这个类型c语言中 当整形变量对待。不建议这么写。 switch(week) { case MON: printf(go to school\n); break; case FRI: printf(to play...\n); break; case SUN: printf(go to sleep\n); break; default: printf(发呆\n); ​ }