# C++的结构体 # 1. 结构体 ① 结构体属于用户自定义的数据类型,允许用户存储不同的数据类型。 ② 语法:struct 结构体名 { 结构体成员列表 } ③ 通过结构体创建变量的方式有三种: 1. struct 结构体名 变量名 2. struct 结构体名 变量名 = { 成员1值,成员2值 } 3. 定义结构体时顺便创建变量 ④ 结构体变量利用点.访问成员 ```python #include using namespace std; #include //自定义数据类型,一些类型的集合组成一个类型 //语法 struct 类型名称 { 成员列表 } //结构体定义的时候,struct关键字不能省略 //1、创建学生数据类型:学生包括(姓名,年龄,分数) struct Student { //成员列表 //姓名 string name; //年龄 int age; //分数 int score; }; int main() { //2.1 struct Student s1 s1类似结构体的实例值,类似变量赋值:int a = 10 → 属性 变量 变量值 //结构体创建的时候,struct 关键字可以省略;上面结构体定义的时候 struct 可以省略 struct Student s1; //给s1属性赋值,通过点.访问结构体变量中的属性 s1.name = "张三"; s1.age = 18; s1.score = 100; cout << "姓名:" << s1.name << "年龄:" << s1.age << "分数:" << s1.score << endl; //2.2 struct Student s2 = { ... } struct Student s2 = { "李四",19,80 }; cout << "姓名:" << s2.name << "年龄:" << s2.age << "分数:" << s2.score << endl; system("pause"); return 0; } ``` 运行结果: - 姓名:张三年龄:18分数:100 - 姓名:李四年龄:19分数:80 - 请按任意键继续. . . ```python #include using namespace std; #include //自定义数据类型,一些类型的集合组成一个类型 struct Student { //成员列表 //姓名 string name; //年龄 int age; //分数 int score; }s3; //2.3 创建结构体的时候,顺便创建个结构体变量 int main() { //2.3 s3.name = "王五"; s3.age = 20; s3.score = 60; cout << "姓名:" << s3.name << "年龄:" << s3.age << "分数:" << s3.score << endl; system("pause"); return 0; } ``` 运行结果: - 姓名:王五年龄:20分数:60 - 请按任意键继续. . . ## 1.1 结构体定义和使用 ① 作用:将自定义的结构体放入到数组中方便维护。 ② 语法:struct 结构体名 数组名[元素个数] = { {},{},...,{} } ```python #include using namespace std; #include //自定义数据类型,一些类型的集合组成一个类型 struct Student { //成员列表 //姓名 string name; //年龄 int age; //分数 int score; }; int main() { //2、创建结构体数组 struct Student stuArray[3] = { {"张三",18,100}, {"李四",28,99}, {"王五",38,66} }; //3、给结构体数组中的元素赋值 stuArray[2].name = "赵六"; stuArray[2].age = 80; stuArray[2].score = 60; //4、遍历结构体数组 for (int i = 0; i < 3; i++) { cout << "姓名:" << stuArray[i].name << "年龄:" << stuArray[i].age << "分数:" << stuArray[i].score << endl; } system("pause"); return 0; } ``` 运行结果: - 姓名:张三年龄:18分数:100 - 姓名:李四年龄:28分数:99 - 姓名:赵六年龄:80分数:60 - 请按任意键继续. . . ## 1.2 结构体数组 ① 作用:将自定义的结构体放入到数组中方便维护。 ② 语法:struct 结构体名 数组名[元素个数] = { {},{},...,{} } ```python #include using namespace std; #include //自定义数据类型,一些类型的集合组成一个类型 struct Student { //成员列表 //姓名 string name; //年龄 int age; //分数 int score; }; int main() { //2、创建结构体数组 struct Student stuArray[3] = { {"张三",18,100}, {"李四",28,99}, {"王五",38,66} }; //3、给结构体数组中的元素赋值 stuArray[2].name = "赵六"; stuArray[2].age = 80; stuArray[2].score = 60; //4、遍历结构体数组 for (int i = 0; i < 3; i++) { cout << "姓名:" << stuArray[i].name << "年龄:" << stuArray[i].age << "分数:" << stuArray[i].score << endl; } system("pause"); return 0; } ``` 运行结果: - 姓名:张三年龄:18分数:100 - 姓名:李四年龄:28分数:99 - 姓名:赵六年龄:80分数:60 - 请按任意键继续. . . ## 1.3 结构体指针 ① 作用:通过指针访问结构体中的成员。 ② 利用操作符 · > 可以通过结构体指针访问结构体属性。 ```python #include using namespace std; #include //结构体指针 //定义学生结构体 struct Student { string name; //姓名 int age; //年龄 int score; //分数 }; int main() { // 1、创建学生结构体变量,这里的 struct 可以省略 struct Student s = { "张三",18,100 }; //2、通过指针指向结构体变量 struct Student* p = &s; //对s取地址, tudent * p 类似 int * p,这里的 struct 可以省略 //3、通过指针访问结构体变量中的数据 //通过结构体指针 访问结构体中的属性,需要利用'->' cout << "姓名:" << p->name << "年龄:" << p->age << "分数:" << p->score << endl; system("pause"); return 0; } ``` 运行结果: - 姓名:张三年龄:18分数:100 - 请按任意键继续. . . ## 1.4 结构体嵌套结构体 ① 结构体中的成员可以是另一个结构体。 ```python #include using namespace std; #include //因为老师的结构体里有学生的结构体,所以学生结构体要在老师结构体前面先定义 //定义学生结构体 struct student { string name; //姓名 int age; //年龄 int score; //分数 }; //定义老师结构体 struct teacher { int id; //教师编号 string name; //教师姓名 int age; //年龄 struct student stu; //学生结构体 }; int main() { //结构体嵌套结构体 //创建老师 teacher t; t.id = 10000; t.name = "老王"; t.age = 50; t.stu.name = "小王"; t.stu.age = 20; t.stu.score = 60; cout << "老师姓名:" << t.name << "老师编号:" << t.id << "老师年龄:" << t.age << "老师辅导的学生姓名:" << t.stu.name << "学生年龄:" << t.stu.age << "学生考试分数:" << t.stu.score << endl; system("pause"); return 0; } ``` 运行结果: - 老师姓名:老王 老师编号:10000 老师年龄:50 老师辅导的学生姓名:小王 学生年龄:20 学生考试分数:60 - 请按任意键继续. . . ## 1.5 结构体做函数参数 ① 作用:将结构体作为参数向函数中传递,传递方式有两种。 ② 传递方式有两种: 1. 值传递 2. 地址传递 ```python #include using namespace std; #include //定义学生结构体 struct student { string name; //姓名 int age; //年龄 int score; //分数 }; //定义老师结构体 struct teacher { int id; //教师编号 string name; //教师姓名 int age; //年龄 struct student stu; //学生结构体 }; //打印学生信息的函数 //1、值传递 void printStudent1(struct student s) { cout << "子函数 值传递前 姓名:" << s.name << "年龄:" << s.age << "分数:" << s.score << endl; s.age = 100; } //2、地址传递 void printStudent2(struct student* p) { cout << "子函数 地址传递前 姓名:" << p->name << "年龄:" << p->age << "分数:" << p->score << endl; p->score = 90; } int main() { //结构体做函数参数 //将学生传入到一个参数中,打印学生身上的所有信息 //创建结构体变量 struct student s; s.name = "张三"; s.age = 20; s.score = 85; cout << "main函数 传递前 姓名:" << s.name << "年龄:" << s.age << "分数:" << s.score << endl; printStudent1(s); cout << "子函数 值传递后 姓名:" << s.name << "年龄:" << s.age << "分数:" << s.score << endl; printStudent2(&s); cout << "子函数 地址传递后 姓名:" << s.name << "年龄:" << s.age << "分数:" << s.score << endl; cout << "main函数 传递后 姓名:" << s.name << "年龄:" << s.age << "分数:" << s.score << endl; system("pause"); return 0; } ``` 运行结果: - main函数 传递前 姓名:张三年龄:20分数:85 - 子函数 值传递前 姓名:张三年龄:20分数:85 - 子函数 值传递后 姓名:张三年龄:20分数:85 - 子函数 地址传递前 姓名:张三年龄:20分数:85 - 子函数 地址传递后 姓名:张三年龄:20分数:90 - main函数 传递后 姓名:张三年龄:20分数:90 - 请按任意键继续. . . ## 1.6 结构体中const使用 ① 作用:const来防止误操作。 ```python #include using namespace std; #include //const 的使用场景 struct student { //姓名 string name; //年龄 int age; //分数 int score; }; //将函数中形参设置为指针,用地址传递,而不是值传递,可以减少内存空间,而且不会复制新的副本 //值传递需要复制新的副本,如果有成千上万个学生调用结构体,会复制成千上个副本 void printStudents(const student* s) { s->age = 150; //报错,因为假如const之后,一旦有修改的操作就会报错,可以防止我们的误操作。 cout << "姓名:" << s->name << "年龄:" << s->age << "分数:" << s->score << endl; } int main() { //创建结构体变量 struct student s = { "张三",15,70 }; //通过函数打印结构体变量信息 printStudents(&s); cout << "main中张三年龄为:" << s.age << endl; system("pause"); return 0; } ``` ## 1.7 结构体案例(一) 案例描述:学校正在做毕设项目,每名老师带领5个学生,总共有3名老师,需求如下:设计学生和老师的结构体,其中在老师的结构体中,有老师姓名和一个存放5名学生的数组作为成员,学生的成员有姓名、考试分数、创建数组存放3名老师,通过函数给每个老师及所带的学生赋值。最终打印出老师数据以及老师所带的学生数据。 ```python #include using namespace std; #include #include //学生结构体定义 struct Student { //姓名 string sName; //学生数组 int score; }; //老师结构体 struct Teacher { //姓名 string tName; //学生数组 struct Student sArray[5]; }; //给老师和学生赋值的函数 void allocateSpace(struct Teacher tArray[], int len) //接收数组的两种方式:一用指针,二用数组名 struct Teacher tArray[] { string nameSeed = "ABCDE"; //给老师开始赋值 for (int i = 0; i < len; i++) { tArray[i].tName = "Teacher_"; tArray[i].tName += nameSeed[i]; //通过循环给每名老师所带的学生赋值 for (int j = 0; j < 5; j++) { tArray[i].sArray[j].sName = "Student_"; tArray[i].sArray[j].sName += nameSeed[j]; int random = rand() % 61 + 40; // 40 ~ 100 tArray[i].sArray[j].score = random; // } } } //打印所有信息 void printInfo(struct Teacher tArray[], int len) { for (int i = 0;i using namespace std; //1、设计英雄结构体 struct Hero { //姓名 string name; //年龄 int age; //性别 string sex; }; //冒泡排序,实现年龄升序排列 void bubbleSort(struct Hero heroArray[], int len) { for (int i = 0; i < len - 1; i++) { for (int j = 0; j < len - i - 1; j++) { //如果j下标的年龄大于j+1下标的元素的年龄,交换两个元素 if (heroArray[j].age > heroArray[j + 1].age) { struct Hero temp = heroArray[j]; //创建一个临时结构体变量 heroArray[j] = heroArray[j + 1]; heroArray[j + 1] = temp; } } } } void printHero(struct Hero heroArray[], int len) { for (int i = 0; i < len; i++) { cout << "姓名:" << heroArray[i].name << " 年龄:" << heroArray[i].age << " 性别:" << heroArray[i].sex << endl; } } int main() { //2、创建数组存放5名英雄 struct Hero heroArray[5] = { {"刘备",23,"男"}, {"关羽",22,"男"}, {"张飞",20,"男"}, {"赵云",21,"女"}, {"貂蝉",19,"女"}, }; int len = sizeof(heroArray) / sizeof(heroArray[0]); cout << "排序前的打印结果" << endl; for (int i = 0; i < len; i++) { cout << "姓名:" << heroArray[i].name << " 年龄:" << heroArray[i].age << " 性别:" << heroArray[i].sex << endl; } //3、对数组进行排序,按照年龄进行升序排序 bubbleSort(heroArray, len); //4、将排序后结果打印输出 cout << "排序后的打印结果" << endl; printHero(heroArray,len); system("pause"); return 0; } ``` 运行结果: - 排序前的打印结果 - 姓名:刘备 年龄:23 性别:男 - 姓名:关羽 年龄:22 性别:男 - 姓名:张飞 年龄:20 性别:男 - 姓名:赵云 年龄:21 性别:女 - 姓名:貂蝉 年龄:19 性别:女 - 排序后的打印结果 - 姓名:貂蝉 年龄:19 性别:女 - 姓名:张飞 年龄:20 性别:男 - 姓名:赵云 年龄:21 性别:女 - 姓名:关羽 年龄:22 性别:男 - 姓名:刘备 年龄:23 性别:男 - 请按任意键继续. . .