C语言结构体

简介

C 数组允许定义可存储相同类型数据项的变量,结构体是 C 编程中另一种用户自定义的可用的数据类型,它允许存储不同类型的数据项。

结构体的一般形式为:

struct 结构体名
{

     成员列表,可以是任何数据类型
};

声明了一个结构体相当于构建了一个新的结构体类型,但系统并不为其分配空间,只有定义结构体变量时才分配内存。

定义结构体变量时,一般形式为:

结构体名  变量名。 例如

struct apple a;

struct 为定义结构体变量的关键字.

三种定义结构体方法

1,

struct person 声明了结构体名字
{
char name[20];
int age;
char sex;
char phone[15];
}p1,p2; 同时定义了两个结构体变量

2,

struct
{
char name[20];
int age;
char sex;
char phone[15];
}p1,p2; 这个只是定义了两个结构图变量,但是没有声明结构体的名字

3,

嵌套结构体
struct date
{
int year;
int monyh;
int day;
};
struct person
{
char name[20];
int age;
char sex;
char phone[15];
struct date brithday;
char *string;
}

总结:定义在前面的是结构体名字,在后面的是变量名字

     引用和初始化结构体变量

一般的形式是:结构图变量.成员名
例子:strcpy(p1.name,“John”);
p1.age=24;

.的作用:.是成员运算符,用于取得结构体中的成员,他在所有的运算符中 优先级最高

结构体数组

  结构体数据就是指数组中的每一个元素都是结构体

#include <stdio.h>
struct test{
  int num ;
  float value;
  char ch;
};
int main()
{
    struct test testArr[3]={ {1,1,2},{3,3,4},{5,5,6} };
    for(int i = 0; i<3 ; i++)
    {
        printf("testArr[%d].num=%d\n",i,testArr[i].num);
        printf("testArr[%d].value=%f\n",i,testArr[i].value);
        printf("testArr[%d].ch=%d\n",i,testArr[i].ch);
    }
    return 0;
}

结构体指针

当一个指针变量指向结构体时,称为结构体指针

struct 结构体名 *变量名;

结构体变量名与数组名不一样,数组名在表达式中会被转换成数组指针,而结构体变量名不会,无论在任何表达式中标表示的都是整个结构体本身,要活的结构体变量的地址,则必须使用取地址符&

#include <stdio.h>
struct test{
    int num;
    char ch;
    double doub;
}t1;
int main()
{
    struct test t1 = {5,'A',5.6};
    struct test *ptr = &t1;
    //解引用和点运算符
    printf("type1:(*ptr).num=%d\n",(*ptr).num);//.的优先级比*高,所以要上括号
    //指针
    printf("type2:  ptr->ch=%c\n",ptr->ch);
    return 0;
}

 字节对齐

结构体中存在内存对齐,作用就是加快系统的访问效率。因为当你定义结构体成员时,由于数据类型的不同,申请的空间大小也不一样。

struct A
{
 int a;//4字节
 short b;//2字节
 int c;//4字节
 char d;//1字节
};

所以结构体原本所占字节是11字节,但是由于存在字节对齐,所以最后应该是16字节。

字节对齐规则

#pragma pack (n)//按照指定n字节对齐规则
  1. 结构体内部任何K字节的基本数据类型相对于结构体首地址的偏移,必须是K的整数倍
  2. 结构体变量的首地址能够被其最大基本类型成员的大小所整除
  3. 结构体的总大小为结构体最宽基本类型成员大小的整数倍
struct A
{
 int a;//4字节
 short b;//2字节
 char d;//1字节
 int c;//4字节
};

在以上结构体中,所占字节最大的数据类型为int,刚开始a申请了4字节空间,到b的时候,其偏移量4刚好是2的整数倍,到d的时候,其偏移量为4+2 = 7,为1的整数倍,到c的时候,其偏移量7不是4的整数倍,所以要加1使其偏移量为8,能够被4整除。至此,结构体实际内存因该是4+2+1+1(多加的,使偏移量刚好为4的整数倍)+4 = 12字节。

字节对齐原因

1,提高结构体成员的访问效率

2,不是所有平台支持随机内存访问

结构体位段

struct person
{
  char num:3  //指定空间中n个比特位,多个位段可以合并使用一个存储空间
};
多个位段使用同一块空间,从低字节到高字节,比特位不够申请新的空间

数据过大,会产生截断
person person ;person.num = 9;9为1001,但num只有3比特,所以产生截断,从低位截断001

  • 0
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

三桶老飞鱼

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值