【C语言--结构体】

  • 结构体的声明,嵌套定义以及引用

#include <stdio.h>
struct stu_st //结构体的声明
{
    char name[20];
    int age;
};                //定义结构体变量p

struct xs_st    //结构体的声明
{
    int am;
    struct stu_st p;  //结构体的嵌套定义

}n1 = { 1,{{"xiaowenfang"},26}}; // 结构体的嵌套初始化,初始化时要按照声明类型顺序对应存放数据
int main()
{
    printf("%d %s %d\n",n1.am,n1.p.name,n1.p.age);//结构体成员的引用
}
  • 结构体的内存对齐---计算结构体的大小

结构体内存对齐原因:结构体的内存对齐拿空间来换取时间的做法。设计结构体的时候让占用空间小的成员尽量集中在一起。

内存对齐的规则:

1. 第一个成员在与结构体变量偏移量为0的地址处。

2. 其他成员变量要对齐到某个数字(对齐数)的整数倍的地址处。

对齐数 = 编译器默认的一个对齐数 与 该成员大小的较小值。

VS中默认的值为8

3. 结构体总大小为最大对齐数(每个成员变量都有一个对齐数)的整数倍。

4. 如果嵌套了结构体的情况,嵌套的结构体对齐到自己的最大对齐数的整数倍处,结构体的整

体大小就是所有最大对齐数(含嵌套结构体的对齐数)的整数倍

简单总结:位置/类型大小能整除

例子:非嵌套结构体大小的计算

c1----------- char 1字节

c2------------int 4字节

d-------------double 8字节

编译器对齐数 8,分别与数据类型相比较 ,数据类型小因此选择 数据类型大小来作为除数。

成员存放:起始位置为0 开始存放c1-----1/4 2/4 3/4 都不能整除----4/4可以整除,因此c2从位置4开始存放------存放d时,8/8能整除,因此d从位置8 开始存放。

计算结构体大小-----首先选出最大对齐数8------存放大小为16---存放大小/最大对齐数 16/8可以整除,因此结构体总大小为16。

嵌套结构体大小的计算:

c1-----char--- 1

s4-----struct S4---16

d------double-----8

含有嵌套结构体的成员存放:起始位置0,存放c1------存放嵌套的结构体时,要找嵌套结构体中的最大对齐数8,并与位置作比较找到能整除的位置,1/8,2/8...7/8都不能整除,8/8可以,因此从位置8开始存放s4-----d的对齐数最小为8,位置24/8整除所以从位置24存放d------此时所占空间一直到位置31,找出所有结构体中的最大对齐数,包括嵌套结构体 ,最大对齐数为8----31/8不能整除,向下找位置32/8可以整除-----结构体的大小为33。

  • 结构体传参

函数传参的时候,参数是需要压栈,会有时间和空间上的系统开销。

如果传递一个结构体对象的时候,结构体过大,参数压栈的的系统开销比较大,所以会导致性能的

下降。

结论:结构体传参,传递地址。

struct S
{
 int data[1000];
 int num;
};
struct S s = {{1,2,3,4}, 1000};
//结构体传参
void print1(struct S s)
{
 printf("%d\n", s.num);
}
//结构体地址传参
void print2(struct S* ps)
{
 printf("%d\n", ps->num);
}
int main()
{
 print1(s);  //传结构体
 print2(&s); //传地址
 return 0;
}

  • 结构体数组

结构体数组是一个数组,由若干个相同类型的结构体变量组成的集合。

定义:struct 结构体名 数组名[ 元素个数 ]

#include <stdio.h>
#define max 10 //使用宏定义,使max = 10
typedef struct student   //使用typedef 将struct student 结构体重新起名为 stu_st  
{
    char a;
    int b;
    char p[10];


} stu_st;
int main()
{
    stu_st prog[max] =   //定义一个结构体数组 
    {
        {12,52,"qwert"},
        {13,53,"qwer"},
        {11,51,"qwe"}


    };
    printf("%s\n",prog[0].p);// 引用数组内结构体的元素。引用方式: 数组名 [下标] . 成员
    
    return 0;
}

  • 结构体指针

结构体指针变量用来存放结构体的地址。

定义方法:

struct 结构体名 * 指针变量名

引用方法:

  1. (*指针变量名).成员

  1. 指针变量名->成员 常用

  • typedef在结构体中的用法--重命名结构体名和指针名

#include<stdio.h>
#define max_st 100
//定义一个结构体  struct stde,结构体变量为s1,s2。
//第一种方式
struct stde
{
    int a;
    char na[max_st];
    float b;
 }s1,s2;  

//第二种方式
struct stde
{
    int a;
    char na[max_st];
    float b;

}; //定义一个结构体
struct stde s1, s2;//定义结构体变量 s1 s2

//第三种方式
typedef struct stde
{
    int a;
    char na[max_st];
    float b;

}stde_st;//使用typedef 将struct stde 重新命名为 stde_st
stde_st s1, s2;//通过 定义两个结构体变量名 s1,s2。

//重命名结构体指针
typedef struct //匿名结构体
{
    int a;
    char na[max_st];
    float b;

}*point_st;//相当于将 struct * 重命名为point_st
point_st p; //相当于struct * p,定义一个结构体指针变量p


//总结:typedef  struct{
//                     }结构体的重命名;  通常与匿名结构体一起使用

//      struct 结构体名 {
//              }变量名;
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值