结构体
结构体中 只要遇到 字符串的 就用 strcpy 进行操作不用 = 因为等号是进行的浅拷贝 只是将地址进行复制而不是复制对象本身
1 作用
> 结构体是一种构造类型的数据结构,是一种或多种基本类型或构造类型的数据的集合
2 定义结构体
语法1
struct 结构体名 { // 定义变量 };
语法2:
定义结构体时顺带创建一个结构体变量
struct 结构体名 {// 定义变量 }结构体变量名;
语法3:
给结构体起别名
typedef struct 结构体名称 { // 定义成员变量 // 可以定义无数个成员变量 }别名;
语法4:
struct{// 定义成员变量// 可以定义无数个成员变量 } 结构体变量名;
3 创建结构体变量
语法1:
struct 结构体名称 结构体变量 = {值1,值2,值3,....}; struct 结构体名称 结构体变量;
语法2:
> 别名 结构体变量 = {值1,值2,值3,....}; > 别名 结构体变量;
注意:
# 结构体对象清0 # memset(&结构体变量名,0,sizeof(struct 结构体名称));结构体初始化 必须按照成员顺序和成员自身类型
4 结构体变量使用其中成员变量
存值结构体变量.成员变量名 = 值;注意:字符串的成员变量需要使用strcpy实现深拷贝
取值结构体变量.成员变量名
5 计算结构体大小
> 对齐方式,默认按照最大的进行对齐数组,结构体将被拆分为存储的数据的大小
示例:
struct Stu {short x; // 4int a; // 4char c; // 4char str[50]; // 47 / 4 = 11 .. 3 = 12 * 4 = 48 };
6 强制对其
作用
默认的结构体的对齐方式是由其中最大的成员进行对齐的使用强制对齐就会使用强制的大小进行对齐
语法
#pragma pack (value)时的指定对齐值value为1 2 4 8等
示例
#include <stdio.h> #pragma pack(2) struct Test {int x; // 4int *p; // 8char c; // 2short s; // 2 }; int main(int argc, char const *argv[]) {printf("%d\n", sizeof(struct Test));return 0; }
特殊结构体
匿名结构体
特点
> 只能创建一个结构体变量
语法:
struct {成员变量;}结构体变量名;
示例
#include <stdio.h> #include <string.h> struct {int age;char color[30]; }ql; int main(int argc, char const *argv[]) {ql.age = 8000;strcpy(ql.color,"黑");printf("年龄:%d\t颜色:%s\n",ql.age,ql.color);return 0; }
整体赋值
> 结构体变量名1 = 结构体变量名2;
> 将结构体变量2的成员的值逐一赋值给结构体变量1的成员
memcpy****函数
作用:拷贝内存中的内容
语法
void *memcpy(void *dest, const void *src, size_t n);参数:dest:目标地址src:资源地址n:长度
结构体定义结构体变量
概念: 结构体A中的成员变量是结构体B的变量
示例:
#include <stdio.h> typedef struct dog {char name[50];char sex[10];int age; } Dog; typedef struct person {char name[50];char sex[10];int age;// 结构体中定义结构体变量Dog dog; } Person; int main(int argc, char const *argv[]) {Dog dog = {"旺财", "公", 3};// 将上面定义的结构体变量dog全赋值给p1中的成员变量dogPerson p1 = {"来福", "男", 18, dog};dog.age = 13;printf("p1的姓名:%s\n", p1.name);printf("p1的性别:%s\n", p1.sex);printf("p1的年龄:%d\n", p1.age);printf("p1 dog的姓名:%s\n", p1.dog.name);printf("p1 dog的性别:%s\n", p1.dog.sex);printf("p1 dog的年龄:%d\n", p1.dog.age);printf("dog的姓名:%s\n", dog.name);printf("dog的性别:%s\n", dog.sex);printf("dog的年龄:%d\n", dog.age);Person p2 = {"常威", "男", 28, {"黑豹", "母", 4}};printf("p2的姓名:%s\n", p2.name);printf("p2的性别:%s\n", p2.sex);printf("p2的年龄:%d\n", p2.age);printf("p2 dog的姓名:%s\n", p2.dog.name);printf("p2 dog的性别:%s\n", p2.dog.sex);printf("p2 dog的年龄:%d\n", p2.dog.age);return 0; }
计算结构体大小
成员变量是结构体其占据的大小也是参与计算对齐单行大小的依据
如
#include <stdio.h> typedef struct Data1 {char c; // 1int a; // 4 8long b; // 8 } D1; // 16 typedef struct Data2 {char c; // 1int i; // 4short s; // 2 16D1 d1; // 16 } D2; // 16+16 = 32 int main(int argc, char const *argv[]) {printf("%d\n", sizeof(D2));return 0; }
结构体指针
概念
指向结构体变量的指针。
语法:
> 结构体名称 *指针变量名;
操作成员变量
指针变量名->成员变量名指针变量名->成员变量名 = 值;注意:字符数组型需要使用strcpy
示例
#include <stdio.h> typedef struct stu {char name[50]; // 48char sex[10]; // 12int age; // 4 } Stu; void chang01(Stu s) {s.age = 29; } void chang02(Stu *s) {s->age = 29; } int main(int argc, char const *argv[]) {Stu s01 = {"张三", "男", 18};Stu *p = &s01;printf("%s\n", p->name);p->age = 19;printf("%d\n", p->age);printf("%d\n", s01.age);// chang01(s01);//全赋值chang02(&s01); // 传递的是地址printf("%d\n", s01.age);return 0; }
指针作为结构体成员
示例1
#include <stdio.h> #include <stdlib.h> #include <string.h> typedef struct stu {char *name;char *sex;int age; } Stu; int main(int argc, char const *argv[]) {char str01[] = "Tom";char str02[] = "man";// Stu s = {str01,str02,19};// printf("s name = %s\n",s.name);// s.name[0] = 't';// printf("str01 = %s\n",str01);// printf("s name = %s\n",s.name);// 成员变量位指针变量如何实现深拷贝Stu s02;s02.name = calloc(50, 1);strcpy(s02.name, str01);s02.sex = calloc(10, 1);strcpy(s02.sex, str02);s02.age = 18;printf("s02 name = %s\n", s02.name);s02.name[0] = 't';printf("str01 = %s\n", str01);printf("s name = %s\n", s02.name);free(s02.name);free(s02.sex);return 0; }
示例2
#include <stdio.h> #include <stdlib.h> #include <string.h> typedef struct stu {char *name;char *sex;int age; } Stu; int main(int argc, char const *argv[]) {Stu *s01 = (Stu *)malloc(sizeof(Stu));s01->name = (char *)malloc(50);s01->sex = (char *)malloc(10);memset(s01, 0, sizeof(Stu));memset(s01->name, 0, 50);memset(s01->sex, 0, 10);strcpy(s01->name, "张三");strcpy(s01->sex, "男");s01->age = 20;printf("姓名:%s\t性别:%s\t年龄:%d\n", s01->name, s01->sex, s01->age);// 如果成员变量是指针,并且是动态开辟内存// 此时如果直接释放该结构体变量会导致内存泄漏// 所以应该先释放里面的成员变量的动态内存,在释放结构体变量的动态内存free(s01->name);free(s01->sex);free(s01);return 0; }
示例3
#include <stdio.h> #include <stdlib.h> #include <string.h> typedef struct dog {char *name;char *sex;int age; } Dog; typedef struct person {char *name;char *sex;int age;Dog *dog; } Person; int main(int argc, char const *argv[]) {Dog *d = (Dog *)calloc(1, sizeof(Dog)); // int d = 1;d->name = (char *)calloc(50, 1);d->sex = (char *)calloc(10, 1);Person *p = (Person *)calloc(1, sizeof(Person));p->name = (char *)calloc(50, 1);p->sex = (char *)calloc(10, 1);p->dog = d; // p->dog = dPerson *p2 = (Person *)calloc(1, sizeof(Person));p2->name = (char *)calloc(50, 1);p2->sex = (char *)calloc(10, 1);p2->dog = d;free(d->name);free(d->sex);free(d);free(p->name);free(p->sex);free(p);free(p2->name);free(p2->sex);free(p2);return 0; }
数组存储结构体变量
示例1
#include <stdio.h> #include <stdlib.h> #include <string.h> typedef struct dog {char name[50];char sex[10];int age; } Dog; int main(int argc, char const *argv[]) {Dog d01 = {"旺财01", "公", 2};Dog d02 = {"旺财02", "公", 2};Dog d03 = {"旺财03", "公", 2};Dog ds[] = {d01, d02, d03};int len = sizeof(ds) / sizeof(ds[0]);for (int i = 0; i < len; i++){ printf("姓名:%s\t性别:%s\t年 龄:%d\n",ds[i].name,ds[i].sex,ds[i].age);}return 0; }
示例2
#include <stdio.h> #include <stdlib.h> #include <string.h> typedef struct dog {char name[50];char sex[10];int age; } Dog; int main(int argc, char const *argv[]) {Dog d01 = {"旺财01", "公", 2};Dog d02 = {"旺财02", "公", 2};Dog d03 = {"旺财03", "公", 2};Dog *ds[] = {&d01, &d02, &d03};int len = sizeof(ds) / sizeof(ds[0]);for (int i = 0; i < len; i++){printf("姓名:%s\t性别:%s\t年龄:%d\n", ds[i]->name, ds[i] - > sex, ds[i]->age);}return 0; }
示例3
#include <stdio.h> #include <stdlib.h> #include <string.h> typedef struct dog {char name[50];char sex[10];int age; } Dog; int main(int argc, char const *argv[]) {Dog *d01 = (Dog *)calloc(1, sizeof(Dog));strcpy(d01->name, "旺财01");strcpy(d01->sex, "公");d01->age = 2;Dog *d02 = (Dog *)calloc(1, sizeof(Dog));strcpy(d02->name, "旺财02");strcpy(d02->sex, "公");d02->age = 2;Dog *d03 = (Dog *)calloc(1, sizeof(Dog));strcpy(d03->name, "旺财03");strcpy(d03->sex, "公");d03->age = 2;Dog *ds[] = {d01, d02, d03};Dog **dss = &ds;for (int i = 0; i < 3; i++){printf("姓名:%s\t性别:%s\t年龄:%d\n", dss[i]->name, dss[i] - > sex, dss[i]->age);free(dss[i]);}return 0; }
示例4
#include <stdio.h> #include <stdlib.h> #include <string.h> typedef struct dog {char name[50];char sex[10];int age; } Dog; Dog **getDogs() {static Dog *dogs[10] = {0};for (int i = 0; i < 10; i++){char name[30] = "旺财";sprintf(name, "旺财%d", i + 1);dogs[i] = (Dog *)calloc(1, sizeof(Dog));strcpy(dogs[i]->name, name);strcpy(dogs[i]->sex, "公");dogs[i]->age = 2;}return &dogs; } int main(int argc, char const *argv[]) {Dog **dogs = getDogs();for (int i = 0; i < 10; i++){printf("姓名:%s\n", dogs[i]->name);}return 0; }
示例5
#include <stdio.h> #include <stdlib.h> #include <string.h> typedef struct dog {char name[50];char sex[10];int age; } Dog; Dog **getDogs() {Dog **dogs = (Dog **)calloc(10, sizeof(Dog *));for (int i = 0; i < 10; i++){Dog *d = (Dog *)calloc(1, sizeof(Dog));char n[30] = {0};sprintf(n, "旺财%d", i + 1);strcpy(d->name, n);printf("d = %p\n", d);dogs[i] = d;}return dogs; } int main(int argc, char const *argv[]) {Dog **dogs = getDogs();for (int i = 0; i < 10; i++){printf("姓名:%s\n", dogs[i]->name);}for (int i = 0; i < 10; i++){free(dogs[i]);}free(dogs);return 0; }