一、struct(结构体)

好的,用更简单的方式解释:在C语言中,struct(结构体)就像是一个小盒子,你可以在里面放不同种类的东西。比如,如果你想同时保存一个人的名字、年龄和薪水,你可以创建一个结构体来做这件事。这就像是你有一个专门的小盒子,里面有三个格子,分别用来放名字、年龄和薪水。

  1. 创建结构体:首先,你得告诉计算机你的盒子长什么样。比如,你可以定义一个Person结构体,里面有name(名字)、age(年龄)和salary(薪水)这三个部分。
struct Person {
    char name[50];
    int age;
    float salary;
};
  1. 使用结构体:定义好之后,你就可以创建这个结构体的实例(就像制作一个这样的盒子)。然后,你可以往里面放东西(设置值),或者从里面取东西(获取值)。
  2. 结构体和指针:你还可以创建一个指向这个盒子的指针,就好比你有一个包含盒子位置的标签,通过它你也可以访问盒子里的东西。
  3. 在函数中使用:这个盒子可以整个传给函数,或者由函数返回,这样在处理很多数据的时候就会方便很多。

简而言之,struct在C语言中就是一种工具,让你可以把不同的数据(比如数字、字符等)打包在一起,方便管理和使用。

另外,typedef关键字常与结构体一起使用,以简化结构体类型的名称。例如:

typedef struct Person {
    char name[50];
    int age;
    float salary;
} Person;

这样,你就可以直接使用Person作为类型名来声明结构体变量,而不是struct Person

示例代码:

(1)首先,在这个例子中,我将定义一个名为“person1”的结构体,它包含一个人的姓名,年龄,身高,体重。然后,我们将创建一个person1类型的变量,并展示如何设置和获取这个变量的字段值。

(2)其次,我将使用指针取出person1中的元素并且打印出来

-a.使用(*pb)方法

struct Person {
	char name[20];
	int age;
	float weight;
	float hight;
  
int main()
{
	struct Person person1 = { "周亚明", 22, 53, 1.77 };

	struct Person* pb = &person1;//定义一个person1的指针变量pb
  
	printf("person1的名字为:%\n", (*pb).name);
	printf("年龄:%d岁,体重:%f千克,身高:%f米\n", (*pb).age, (*pb).weight, (*pb).hight);
	printf("周亚明要健身增重了,一年后。。。。。。\n");
	person1.weight = 70;
	printf("增重后的体重为:%f\n", (*pb).weight);
	return 0;
}

-b.使用pb->方法

printf("person1的名字为:%\n", pb->name);
printf("年龄:%d岁,体重:%f千克,身高:%f米\n", pb->age, pb->weight, pb->hight);
printf("周亚明要健身增重了,一年后。。。。。。\n");
person1.weight = 70;
printf("增重后的体重为:%f\n", pb->weight);


*pb)和pb->的区别:

结构体变量与成员的访问(使用点.操作符)和通过结构体指针访问成员(使用箭头->操作符)之间的区别主要在于它们是如何引用结构体的。

  1. 结构体变量.成员 (variable.member):
  • 这种方式用于直接访问结构体的成员。
  • 当你有一个结构体变量时,你可以使用点.操作符来访问其内部的成员。
  • 例如,如果person是一个Person类型的结构体变量,并且有一个成员age,你可以这样访问它:person.age
  1. 结构体指针->成员 (pointer->member):
  • 这种方式用于通过指向结构体的指针来访问结构体的成员。
  • 当你有一个指向结构体的指针时,你需要使用箭头->操作符来访问指针所指向的结构体的成员。
  • 例如,如果personPtr是一个指向Person类型的结构体的指针,你可以这样访问age成员:personPtr->age

在实际使用中,选择哪种方式取决于你是直接拥有一个结构体变量,还是拥有一个指向结构体的指针。从语法上来说,pointer->member等价于(*pointer).member。当使用指针时,箭头操作符->提供了一种更为简洁和清晰的方式来访问成员,而不需要手动解引用指针。

我的疑问:直接拥有一个结构体变量和拥有一个指向结构体的指针有什么区别?

直接拥有一个结构体变量和拥有一个指向结构体的指针之间的主要区别在于它们如何存储和访问数据:

  1. 直接拥有一个结构体变量
  • 当你直接声明一个结构体变量时,结构体的整个数据(所有成员)都存储在栈上(或者在声明它的作用域内的内存中)。
  • 你可以直接通过变量名和点.操作符来访问结构体的成员。
  • 结构体变量持有实际的数据。例如,struct Person person;声明了一个Person类型的结构体,并且person包含了这个结构体的实际数据。
  1. 拥有一个指向结构体的指针
  • 当你有一个指向结构体的指针时,这个指针只存储结构体数据的地址,而不是数据本身。
  • 结构体的实际数据可以存储在栈上,也可以通过动态内存分配(如malloc)存储在堆上。指针只是指向这个数据的位置。
  • 你需要使用箭头->操作符通过指针访问结构体的成员。
  • 指针变量自身占用的内存较小,只存储一个地址。例如,struct Person *personPtr;声明了一个指向Person类型结构体的指针,personPtr存储的是地址,而不是实际的Person数据。

使用指针的优势包括:

  • 内存效率:特别是对于大型结构体,使用指针可以避免复制整个结构体的开销,因为指针只需复制地址。
  • 灵活性:指针可以被赋予新的地址,指向不同的结构体实例,也可以用于动态内存分配,这在处理大量数据或在不确定数据大小时非常有用。
  • 支持动态数据结构:例如链表和树等数据结构通常需要使用指针。

直接使用结构体变量则更直观、简单,适用于结构体较小或者生命周期较短的情况。这样可以直接在栈上快速分配和释放内存,而不需要担心内存管理的复杂性。

更改字符串的代码-->person1.name

strcpy_s(person1.name ,sizeof(person1.name), "彭于晏");

运行结果:

C语言学习第八天_操作符