<c语言学习>结构体

结构体类型

        为什么要有结构体

                我们用c语言描述年龄时候,可以定义一个整形类型来实现:

int age;
age = 18;
printf("年龄为%d",age);

(c语言描述年龄)

                由于年龄这一属性比较单一,类似性别、某游戏角色攻击力、血量都可以用c语言内置的变量来描述。

                但是如果现在需要描述一本书或一个游戏装备,这种有多种属性的角色,只用一个变量看起来就不够用了,我们需要一种方式(结构体)来描述他们:

                例如描述一本书,我们可以这样说:“书的名字是xxx,书的作者是xxx,书的总页数是xxx”,这时我们需要定义一个结构体类型,以描述这些属性。

        结构体类型定义,初始化,使用

                结构体定义

                        以下是定义一个用来描述书的结构体类型,模样如下:
 

//struct 表示结构体 book 表示结构体类型名称
struct book
{//此处为自定义结构体类型“book” 的属性们char name[20];char writer[20];int n;
}
                结构体初始化
//前面定义了结构体变量类型,现在用定义好的类型创建一个结构体:
struct book doom; //"wtruct book"表示类型  “doom”表示结构体变量名//结构体初始化类似于普通变量的初始化:
int a; //“int”表示类型 “a”表示变量名doom.n = 30;//赋值结构体doom中的n(书的页数)strcpy(doom.name,"老人与海")//f赋值结构体doom中的name(书名)
                结构体使用
printf("%d",doom.n);//打印书的页数

结构体对齐

        为什么要有结构体对齐

                假如我们现在有这样的一个结构体:

struct test//定义类型
{char a;int b;int c;int d;
}struct test A;//创建一个结构体A

                

      我们可能想象的A在内存中是这样放的:

        对于我们来说一目了然,但是对于计算机读取来说就麻烦了,假如现在有一个机器,他一次可以读四个字节,那么他访问结构体A可能需要七次才能读完:

        我们可以通过某种规则让他变成方便计算机读取的存储形式:

        空间换时间,用三个字节的代价,让计算机读取这个结构体用的次数减少了三次。

        对齐规则

      以下是结构体对齐规则的基本要点:

  1. 首个成员对齐

    • 结构体的第一个成员总是从结构体变量的起始地址开始存放,偏移量为0。
  2. 成员对齐规则

    • 后续每个成员在结构体中的偏移量需要是对齐数的整数倍,其中对齐数一般等于该成员的大小或编译器默认的对齐数(机器相关的最小对齐单位)两者中的较小值。
    • 比如,如果一个结构体里有一个int成员,而在当前平台上int大小为4字节且默认对齐单位也为4字节,那么该int成员将被放在4字节对齐的位置上。
  3. 结构体大小对齐

    • 结构体的总大小(包括可能存在的填充字节)需要是所有成员中最大对齐数的整数倍。
    • 结构体末尾可能会添加额外的字节作为填充,以满足上述对齐要求。
  4. 结构体自身的对齐值

    • 结构体的有效对齐值通常是其所有成员中最大对齐值的成员的对齐值,确保整个结构体实例的起始地址也符合这个最大对齐值的要求。
    • 当结构体组成数组时,结构体之间的间隔也将按照结构体的有效对齐值来确定。
  5. 编译器控制

    • 许多编译器允许通过预编译指令(如C/C++中的#pragma pack(n))来指定自定义的对齐值,这样会暂时改变当前作用域内的结构体对齐策略。

        

结构体位段

        为什么要有结构体位段

                假如有这样的一个结构体类型:
                

//类型名称考试成绩
struct Scores
{int math;int english;int chinese;
}

                一般来说,一个成绩只需要三位数就可以描述,也就是只需要八个机器码(比特)完全够用了,而一个int类型要占用32个机器码(比特),这样就显得很浪费了。

                为了解决这个问题(节省空间),我们可以使用结构体位段。简单来说,就是让变量们挤一挤。比如上面的Scores结构体,让三科的成绩挤在一个整形int里。

        

                这样浪费的空间就少了很多,用位段定义这个成绩结构体类型如下:
 

struct Scores
{int :math;int :english;int :chinese;
}

        结构体位段规则(不同编译器有所差异)

        结构体位段(Bit-field)是C语言中一种特殊的数据结构,允许在一个整型变量(通常为intunsigned int)内划分多个命名的位区域。位段的规则主要包括:

  1. 声明格式: 在结构体中定义位段时,格式如下:

    struct {type member_name : bit_width;// 其他位段...
    } variable_name;

  2. 其中,type是位段成员的类型,但实际存储时会被隐式转换为足够容纳所有位段的整型类型;member_name是位段的名称;bit_width是在该位段中使用的位数。

  3. 分配顺序: 位段成员在内存中按照声明顺序从左向右分配,但不同的编译器可能会有不同的分配策略,有的是从最低有效位(LSB)开始分配,有的是从最高有效位(MSB)开始分配。

  4. 位段宽度: bit_width指定的位数不能超过成员类型的位宽。例如,在32位系统中,一个int类型的位段的宽度范围是1到32。

  5. 未指定宽度: 如果省略位宽,则大多数编译器会根据成员类型自动选择合适的位宽,直到填满包含位段的整数。

  6. 存储开销: 编译器会尽可能紧凑地安排位段,但可能会在位段之间加入额外的位作为填充,以便于整体对齐,并且至少会分配一个完整的基本整型变量的空间(如一个int)来存储所有位段。

  7. 跨边界行为: 不同编译器对于位段跨越一个基本整型变量边界的处理方式不同。有些编译器会在下一个整型变量中继续分配,而有些则可能不支持跨越边界。

  8. 初始化和赋值: 可以初始化位段,但赋值时要注意仅修改指定位段的位,不会影响同一存储单元内其他位段的值。

  9. 跨平台差异: 位段的具体行为依赖于编译器实现,因此在不同平台和编译器之间可能存在显著差异,编写可移植的位段代码时需特别小心。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/283405.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

亚马逊AWS展示高效纠错的全新量子比特!

亚马逊网络服务公司(AWS)在量子计算的纠错技术领域取得了显著成就,极大地简化了量子系统的复杂性和资源需求。他们的研究人员通过采用“双轨擦除”量子比特(dual-rail erasure qubit)技术,有效地克服了量子…

Flink入门知识点汇总(二)

具体内容请看b站尚硅谷课程! 32_Flink运行时架构_提交流程_Yarn应用模式_哔哩哔哩_bilibili 窗口 Flink的窗口并不是静态准备好的,而是动态创建的。数据流到达时不会准备24个或者其他完整数量的桶,而是当下桶接满了,才临时又拿新…

(C语言)浮点数在内存中的存储详解

1. 浮点数 常见的浮点数:3.14159、 1E10等 ,浮点数家族包括: float、double、long double 类型。 浮点数表示的范围: float.h 中定义. 2. 浮点数的存储 我们先来看一串代码: int main() {int n 9;float* pFloa…

分页多线程处理大批量数据

1.业务场景 因为需要从一个返利明细表中获取大量的数据,生成返利报告,耗时相对较久,作为后台任务执行。但是后台任务如果不用多线程处理,也会要很长时间才能处理完。 另外考虑到数据量大,不能一次查询所有数据在内存…

分布式Raft原理详解,从不同角色视角分析相关状态

分布式Raft原理详解,从不同角色视角分析相关状态 1. CAP定理2.Raft 要解决的问题3. Raft的核心逻辑3.1. Raft的核心逻辑2.1. 复制状态机2.2. 任期 Term2.3. 任期的意义:逻辑时钟2.4 选举定时器 3. Leader选举逻辑4. 从节点视角查看Leader选举4.1. Follow…

qt+ffmpeg 实现音视频播放(三)之视频播放

一、视频播放流程 (PS:视频的播放流程跟音频的及其相似!!) 1、打开视频文件 通过 avformat_open_input() 打开媒体文件并分配和初始化 AVFormatContext 结构体。 函数原型如下: int avformat_open_inpu…

ideaSSM 工程车辆人员管理系统bootstrap开发mysql数据库web结构java编程计算机网页源码maven项目

一、源码特点 idea 开发 SSM 工程车辆人员管理系统是一套完善的信息管理系统,结合SSM框架和bootstrap完成本系统,对理解JSP java编程开发语言有帮助系统采用SSM框架(MVC模式开发),系统具 有完整的源代码和数据库&…

[AIGC] 在Spring Boot中指定请求体格式

在使用Spring Boot开发Web应用的时候,我们经常会遇到需要接收并处理HTTP请求的情况。一个HTTP请求通常包括一个请求行、若干请求头和一个请求体。请求体在POST和PUT请求中特别重要,因为它通常用于向服务器传递数据。 文章目录 创建并使用一个Java Bean指…

计算机二级Python基础操作题

题目来源:计算机二级Python半个月抱佛脚大法(内呈上真题版) - 知乎 第4,5,6,7,9,10,11套 1. 基础题1 sinput() print("{:\"^30x}".format(eval(s))) b …

【S5PV210】 | GPIO编程

【S5PV210】 | GPIO编程 时间:2024年3月17日22:02:32 目录 文章目录 【`S5PV210`】 | `GPIO`编程目录1.参考2.`DataSheet`2.1.概述2.1.1.特色2.1.2 输入/输出配置2.1.3 `S5PV210` 输入/输出类型2.1.4 IO驱动强度**2.1.4.1 类型A IO驱动强度****2.1.4.2 类型A IO驱动强度****2…

Selenium不同版本配置自动下载驱动及打包细节

Selenium配置浏览器驱动 自动下载浏览器驱动的方法 selenium4.7.0自动下载浏览器驱动的方法 selenium4.11.0 或4.11.1手动设置浏览器驱动路径的方法pyinstaller打包程序时同时打包ChromeDriverchromedriver路径需要sys._MEIPASS的路径进行引用方法一:通过–add-data…

LiveGBS流媒体平台GB/T28181功能-HTTPS 服务支持配置开启什么时候需要开启HTTPS测试SSL证书配置HTTPS测试证书

LiveGBS功能支持HTTPS 服务支持配置开启什么时候需要开启HTTPS测试SSL证书配置HTTPS测试证书 1、配置开启HTTPS1.1、准备https证书1.1.1、选择Nginx类型证书下载 1.2、配置 LiveCMS 开启 HTTPS1.2.1 web页面配置1.2.2 配置文件配置 2、HTTPS测试证书3、验证HTTPS服务4、为什么要…

安防监控视频汇聚平台EasyCVR接入海康Ehome设备,设备在线但视频无法播放是什么原因?

安防视频监控/视频集中存储/云存储/磁盘阵列EasyCVR平台可拓展性强、视频能力灵活、部署轻快,可支持的主流标准协议有国标GB28181、RTSP/Onvif、RTMP等,以及支持厂家私有协议与SDK接入,包括海康Ehome、海大宇等设备的SDK等。平台既具备传统安…

python5:基于多进程的并发编程、基于协程的并发编程的学习笔记

进程 为什么要使用多进程?——GIL的存在,多线程实际不是并发执行 将任务分为两类:IO密集型(多线程)CPU密集型(多进程) 多进程的基本用法 concurrent.futures.process.ProcessPoolExecutor#进…

Airgorah:一款功能强大的WiFi安全审计工具

关于Airgorah Airgorah是一款功能强大的WiFi安全审计工具,该工具可以轻松发现和识别连接到无线接入点的客户端,并对特定的客户端执行身份验证攻击测试,捕捉WPA握手包,并尝试破解接入点的密码。在该工具的帮助下,广大研…

C语言联合体和枚举

前言 这篇博客就把剩下的两个自定义类型联合体和枚举好好总结一下,让我们好好看看联合体和枚举到底是什么 个人主页:小张同学zkf 若有问题 评论区见 感兴趣就关注一下吧 目录 1. 联合体 1.1 联合体类型的声明 1.2 联合体的特点 1.3 相同成员的结构体和联…

分类预测 | Matlab实现PSO-KELM粒子群优化算法优化核极限学习机分类预测

分类预测 | Matlab实现PSO-KELM粒子群优化算法优化核极限学习机分类预测 目录 分类预测 | Matlab实现PSO-KELM粒子群优化算法优化核极限学习机分类预测分类效果基本描述程序设计参考资料 分类效果 基本描述 1.MATLAB实现PSO-KELM粒子群优化算法优化核极限学习机分类预测(完整源…

ideaSSM 高校公寓交流员管理系统bootstrap开发mysql数据库web结构java编程计算机网页源码maven项目

一、源码特点 idea 开发 SSM 高校公寓交流管理系统是一套完善的信息管理系统,结合SSM框架和bootstrap完成本系统,对理解JSP java编程开发语言有帮助系统采用SSM框架(MVC模式开发),系统具有完整的源代码和数据库&…

C语言:自定义类型(结构体)

目录 一、结构的特殊声明二、结构的自引用三、结构体内存对齐1.对齐规则2.为什么存在内存对齐(1)平台原因 (移植原因):(2)性能原因: 3.修改默认对齐数 四、结构体传参五、结构体实现位段1.什么是位段2.位段的内存分配3.位段的跨平台问题4.位段使用的注意…

硬件工程师入门基础知识(四)多层陶瓷电容应用(三)

多层陶瓷电容应用(三) 1.开关电源输出滤波电容器如何选择和计算?2.线性电源和开关电源对于滤波电容的选择有何区别?3.哪些电路适合三端多层陶瓷电容?4.哪些电路适合金属支架多层陶瓷电容?1.开关电源输出滤波电容器如何选择和计算? 无论任何开关电源拓扑,其输出滤波的目…