定义一个结构体类型
struct Teacher{
char name[64];
int age;
int id
};
这样相当于是定义了一个数据类型,但是还没有进行内存空间的分配,在定义的数据类型来定义变量的名称的时候就会 进行内存空间的分配。
struct Teacher T;
这样就定义了变量,并且分配了内存。
这样定义结构体变量有些麻烦,因此可以使用typedef来进行重定义
typedef struct Teacher{
char name[64];
int age;
int id
}Teacher;
Teacher T;
这样就可以省略struct关键字的书写了。
用结构体类型定义变量的方法有三种,最上面的是第一种,另外一种是可以在定义结构体的时候定义变量,还有一种是定义没有名字的结构体,是第二种的特殊情况。
初始化结构体变量的三种方法。
第一种是定义变量的时候给变量赋值。
第二种方法是和匿名绑定在一起。
第三种方法是定义结构体的时候定义变量的时候进行初始化。
变量的引用:
可以使用.引用,如果是指针变量,可以使用->来进行引用。
.操作符是寻址操作符,计算age相对于T大变量的偏移量。计算实在cpu中进行,没有操作内存。
->运算符也是在进行寻址,并没有操作内存,只有在进行赋值的时候才操作内存,其他的都是通过地址读取内存中的内容。
结构体的赋值=操作编译器提供的行为
一般类型是可以进行直接对应赋值的。
结构体做函数参数的时候所遇到的问题和一般变量做函数参数遇到的问题是一致的,就是所谓的在不同的栈空间分配不同的局部变量,如果想要操作主调函数中的变量,需要将主调函数变量的地址传递给被调用函数。这个就是函数参数传递的本质 ,函数调用要想到函数调用的内存模型。
结构体变量做函数参数和结构体指针做函数参数的本质区别就是变量做参数和变量的指针作为参数的区别。也就是被调用函数如何操作主调函数分配的内存空间。
要清楚的知道内存分配在哪些地方,是栈上,还是堆上,还是常量区,这个很重要。
结构体里面可以嵌套多级指针,要注意一定要提前分配好内存空间。
记得分配完内存空间之后要记得判断是否分配内存成功,要做到一个入口,一个出口,不要有一个入口,多个出口,这样不便于管理。
在字符串进行内存分配的时候别忘了给字符串后面添加一个' '
结构体中的深浅拷贝,指的是进行复制的时候,仅仅是值的复制,但是如果是一个指针变量,那么赋值过去的只会是一个地址,当你释放这个地址空间的时候,另外一个指针变量仍在,因此,在此释放这个指针变量就会报错。
C++编译器提供的=操作是浅拷贝,仅仅是将值进行拷贝,不会涉及到内存空间的相关问题
结构体中的偏移量问题就是编译器解释内存空间的问题。
一旦结构体定义下来,结构体中的成员的内存布局就定义下来了,可以通过内部成员的地址从而得到大的结构体的地址。
可以通过NULL这个指针来求出结构体中成员的偏移量。
C语言中的强制类型转换真的很强大。