结构体(结构体内存对齐)+位段+枚举

这篇具有很好参考价值的文章主要介绍了结构体(结构体内存对齐)+位段+枚举。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

本期带大家一起来学习一下结构体知识+位段知识+枚举知识🌈🌈🌈

1.结构体📌📌

1.1 结构体的声明✈️✈️

1.1.1 结构体的完全声明🚀

结构体是一种自定义的类型,🔦🔦
结构体是将不同类型的数据按照一定的功能需求进行整体封装
,封装的数据类型与大小均可以由用户指定。
那么又该如何声明一个结构体呢⁉️⁉️⁉️
声明一个结构体如下:

struct 结构体名
{
成员列表
};

#include<stdio.h>
struct stu
{
	char name[20];
	int age;
	float score; 
}s1;
int main()
{
	struct stu s={"Brown",18,94.0f };
	return 0;
}

对于s1来说,s1是全局变量❗️❗️❗️
然而s是一个局部变量</font❗️❗️❗️

然而当我们觉得我们定义的结构体的名字过于复杂的时候,
我们可以使用typedef关键字
作用是为一种数据类型定义一个新名字⚠️⚠️

#include<stdio.h>
typedef struct Stu
{
	char name[20];
	int age;
	float score; 
}stu;
int main()
{
	 stu s={"Brown",18,94.0f };
	return 0;
}

注意:
typedef用于重定义一个结构体名称时,
分号之前的stu是 结构体的名称🌴🌴🌴
不同于上面提到的 全局变量❗️❗️❗️

1.1.2 结构体的不完全声明🚀🚀

对于一个结构体来说,还可以对其不完全声明,省略结构体的名称🍭🍭

换句话说,也即是 匿名结构体
对于 匿名结构体来说,定义的变量是 一次性的🍭🍭🍭

#include<stdio.h>
 struct 

{
	char name[20];
	int age;
	float score; 
}stu;
int main()
{
	 stu s={"Brown",18,94.0f };
	return 0;
}

接下来我们看看下面的代码是否正确

#include<stdio.h>
 struct 
{
	char name[20];
	int age;
	float score; 
}stu;
 struct 
{
	char name[20];
	int age;
	float score; 
}*p;
int main()
{
	 stu s={"Brown",18,94.0f };
	 p=stu;
	return 0;
}

结构体(结构体内存对齐)+位段+枚举
对于第一个struct stu报错的原因是,该结构体是一个匿名结构体
对于第二个p=stu报错的原因是
编译器会把上面的两个声明当成完全不同的两个类型🍑🍑🍑
所以是非法的🚩🚩🚩

1.2 结构体的自引用✈️✈️

结构体的自引用是自生包含一个类型为该结构本身的成员
这个便是🎷🎷链表🎷🎷
相关知识会在后续发出哈哈哈哈
具体代码如下:
结构体(结构体内存对齐)+位段+枚举

1.3 结构体的内存对齐✈️✈️

1.3.1 结构体的内存对齐计算🚀🚀

结构体的基本使用我们已经学会了
接下来我们来通过sizeof计算结构体的大小🔔🔔🔔

💡💡结构体的对齐规则
(1)第一个成员存放在永远在偏移量为0的位置📍
(2)从第二个成员开始,在其自身对齐数的整数倍开始存储📍📍
对齐数=编译器默认对齐数和成员字节大小的最小值,
VS编译器默认对齐数为8,gcc环境下没有默认对齐数
(3)结构体变量所用总空间大小是成员中最大对齐数的整数倍。📍📍📍
(4)当遇到嵌套结构体的情况,嵌套结构体对齐到其自身成员最大对齐数的整数倍,结构体的大小为当下成员最大对齐数的整数倍。📍📍📍📍

💡💡接下来我们来看几个题目,计算结构体的大小✒️✒️
结构体(结构体内存对齐)+位段+枚举
结构体(结构体内存对齐)+位段+枚举

结构体(结构体内存对齐)+位段+枚举

结构体(结构体内存对齐)+位段+枚举

显然我们通过画图得出来的结果和计算出来的结果是一模一样的
那我们接下来看这个题目💬💬💬💬
结构体当中又嵌套了一个结构体🍏🍏🍏
那么又该如何解决呢❓❓❓
其实本质是一样的

结构体(结构体内存对齐)+位段+枚举
结构体(结构体内存对齐)+位段+枚举
这里的话可能会有小伙伴觉得这是25,但是需要明白的是
结构体内存的大小要为成员当中最大对齐数的整数倍

1.3.2 为什么存在结构体内存对齐🚀🚀

1. 平台原因(移植原因):🔍 🔎
不是所有的硬件平台都能访问任意地址上的任意数据的;
某些硬件平台只能在某些地址处取某些特定类型的数据,否则抛出硬件异常
2. 性能原因🔍 🔎
数据结构(尤其是栈)应该尽可能地在自然边界上对齐。
原因在于,为了访问未对齐的内存,处理器需要作两次内存访问;而对齐的内存访问仅需要一次访问
CPU在读取数据的时候,每次是按照 4个字节 读取的
为了提高性能,通过浪费空间来提高性能
举个例子💬💬💬
结构体(结构体内存对齐)+位段+枚举
这种情况下为了拿到int当中的数据时候,要进行二次读取,性能不高

然而在这种情况下只需要读取一次就可以拿到int当中存放的数据
结构体(结构体内存对齐)+位段+枚举

那在设计结构体的时候,我们既要满足对齐,又要节省空间,如何做到:
让占用空间小的成员尽量集中在一起

1.4 修改默认对齐数✈️✈️

前面提到, VS环境下的默认对齐数是8,gcc环境下没有默认对齐数
那么在VS环境下我们是否可以修改默认对齐数呢
答案是有的
结构体(结构体内存对齐)+位段+枚举
代码如下

#include <stdio.h>
#pragma pack(8)//设置默认对齐数为8
struct S1
{
	char c1;
	int i;
	char c2;
};
#pragma pack()//取消默认对齐数的重设置,还原默认值
int main()
{
	printf("struct stu 大小为%d\n", sizeof(struct S1));
	return 0;
}

2. 位段📌📌

2.1 位段介绍✈️✈️

1.位段的成员必须是 int、unsigned int 或signed int 。
2.位段的成员名后边有一个冒号和一个数字。

结构体(结构体内存对齐)+位段+枚举

💬💬 那么位段的大小如何计算呢???
对于位段的计算,C语言没有明确规定位段在内存当中是如何让存储的
这和编译器有关系的
对于VS来说
优先使用低位的bite位,再使用高位的bite位
当剩下的bite位不够下一个所需要的位的时候,会再次开辟一个字节的空间 结构体(结构体内存对齐)+位段+枚举

跟结构相比,位段可以达到同样的效果,但是可以很好的节省空间,但是有跨平台的问题存在

2.2 位段跨平台问题✈️✈️

注意!!!

  1. int 位段被当成有符号数还是无符号数是不确定的。
  2. 位段中最大位的数目不能确定。(16位机器最大16,32位机器最大32,写成27,在16位机器会出问题。3. 位段中的成员在内存中从左向右分配,还是从右向左分配标准尚未定义。
  3. 当一个结构包含两个位段,第二个位段成员比较大,无法容纳于第一个位段剩余的位时,是 舍弃剩余的位还是利用,这是不确定的❗️❗️❗️

3. 枚举📌📌

3.1枚举的定义✈️✈️

枚举便是一一列举
生活当中,性别和星期几都是可以列举的

结构体(结构体内存对齐)+位段+枚举

✔️✔️✔️我们还可以对枚举的类型取值, 默认开始第一个是1,接下来依次加1✔️✔️✔️

3.2 枚举的优点✈️✈️

枚举的优点:

  1. 增加代码的可读性和可维护性🌱
  2. 和#define定义的标识符比较枚举有类型检查,更加严谨。🌱🌱
  3. 防止了命名污染(封装)🌱🌱🌱
  4. 便于调试🌱🌱🌱🌱
  5. 使用方便,一次可以定义多个常量🌱🌱🌱🌱🌱

4. 感谢与交流📌📌

🌹🌹🌹如果大家通过本篇博客收获了对结构体及枚举,特别是结构体内存对齐和位段在VS当中的存储有了新的认知,那么希望支持一下哦如果还有不明白的,疑惑的话,或者什么比较好的建议的话,可以发到评论区,
我们一起解决,共同进步 ❗️❗️❗️
最后谢谢大家❗️❗️❗️💯💯💯

结构体(结构体内存对齐)+位段+枚举文章来源地址https://www.toymoban.com/news/detail-409933.html

到了这里,关于结构体(结构体内存对齐)+位段+枚举的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • C语言自定义类型 — 结构体、位段、枚举、联合

    本期主要对通讯录三篇博客文章进行补充 通讯录文章:通讯录系列文章 对 结构体 进行详细介绍,其次讲解位段、枚举、联合体 在C语言中,结构是一种用户自定义的数据类型,它可以由不同类型的数据成员组成,每个数据成员可以是不同的数据类型。 结构的作用是将多个不

    2024年02月14日
    浏览(27)
  • 【C语言:自定义类型(结构体、位段、共用体、枚举)】

    C语言已经提供了内置类型,如:char、short、int、long、float、double等,但是只有这些内置类型还是不够的, 假设我想描述学生,描述⼀本书,这时单⼀的内置类型是不⾏的。描述⼀个学生需要名字、年龄、学号、身高、体重等;描述⼀本书需要作者、出版社、定价等。C语言为

    2024年02月05日
    浏览(29)
  • C/C++之自定义类型(结构体,位段,联合体,枚举)详解

    专栏分类:C语言初阶      C语言程序设计————KTV       C语言小游戏     C语言进阶 C语言刷题 欢迎大家点赞,评论,收藏。 一起努力,一起奔赴大厂。 目录 个人主页:点我进入主页   1.前言 2.结构体 2.1结构体声明 2.2结构体初始化 2.3结构体的自引用 2,4结构体的内存

    2024年02月08日
    浏览(27)
  • 一篇博客学会系列(2)—— C语言中的自定义类型 :结构体、位段、枚举、联合体

    目录  前言 1、结构体 1.1、结构体类型的声明 1.2、特殊的结构体类型声明 1.3、结构体的自引用 1.4、结构体的定义和初始化 1.5、结构体成员变量的调用 1.6、结构体内存对齐  1.6.1、offsetof 1.6.2、结构体大小的计算 1.6.3、为什么存在内存对齐?  1.7、 修改默认对齐数 1.8、结构

    2024年02月08日
    浏览(30)
  • 结构体内存对齐(面试重点)

    1.1 结构体的概念 结构是⼀些值的集合,这些值称为成员变量。结构的每个成员可以是不同类型的变量。 1.1.1 结构的声明 例如描述⼀个学⽣: 1.1.2 结构体变量的创建和初始化 运行结果如图: 1.2 结构的特殊声明 在声明结构的时候,可以不完全的声明。 比如: 上⾯的两个结构

    2024年01月25日
    浏览(32)
  • C语言之结构体内存对齐与内存的简单理解

    文章目录 内存单元的理解 结构体中内存对齐的规则 为什么会存在内存对齐 首先先要介绍一下C语言中一些常见的存储单元     bit       存放一个二进制位     Byte   1Byte = 8 bit     KB     1KB   = 1024 Byte     MB     1MB   = 1024 KB     GB     1GB   = 1024 MB     TB 

    2023年04月26日
    浏览(28)
  • C语言——结构体类型(二)【结构体内存对齐,结构体数组】

    📝前言: 上一讲结构体类型(一)中,我们讲述了有关 结构体定义,创建,初始化和引用 的内容,这一讲,我们进一步学习结构体的相关知识: 1,结构体内存对齐 2,结构体数组 🎬个人简介:努力学习ing 📋个人专栏:C语言入门基础 🎀CSDN主页 愚润求学 🌄每日鸡汤:

    2024年01月24日
    浏览(54)
  • 【C语言】位段枚举联合

    鹅,鹅,鹅,曲项向天歌。白毛浮绿水,红掌拨清波。 — 唐代·骆宾王《咏鹅》 这篇博客我们会详细介绍位段,以及枚举类型和联合类型 位段的声明和结构是类似的,有两个不同: 1.位段的成员必须是 int、unsigned int 或signed int 以及 char或unsigned char。 2.位段的成员名后边有一

    2024年02月15日
    浏览(25)
  • 【刷题笔记】结构体内存对齐举例+统计回文

    题目: 下面存在两个结构体: 在#pragma pack(4)和#pragma pack(8)的情况下, 结构体的大小 分别是? 分析:         C/C++中结构体计算其大小涉及到内存对齐问题。(详细可以参考我这篇博客:结构体、位段、共用体、枚举相关内存知识(c语言)_柒海啦的博客-CSDN博客)         这

    2024年02月03日
    浏览(26)
  • C语言如何计算结构体大小(结构体的内存对齐)

    结构体的内存对齐是有关结构体内容的很重要一个知识点,主要考察方式是计算结构体的字节大小。 当我们对计算结构体一无所知,我们不妨自己思索如何计算,是不是直接计算结构体成员变量占用内存的大小呢? 那我们先举个例子  观察发现结构体的大小计算跟我们想的

    2024年02月16日
    浏览(32)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包