当前位置: 首页 > news >正文

【C/C++】如何求出类对象的大小----类结构中的内存对齐


每日激励:“不设限和自我肯定的心态:I can do all things。 — Stephen Curry”

绪论​:
通过本章你能具体的了解到,如何计算出一个类的大小,并且了解其中到底是如何算的以及了解到为什么需要内存对齐这种算!
————————
早关注不迷路,话不多说安全带系好,发车啦(建议电脑观看)。

类对象的大小

  • 类对象的大小来说仅由成员影响,成员函数不影响:
  • 因为:在C++中成员函数实际上是在编译时被解析并绑定到特定的对象上,通过对象来调用这些方法并不会增加对象本身的存储需求。
  • 具体来说,在创建一个类的实例时,只有成员变量会被分配内存空间,而成员函数则存在于程序的代码段中。即使增加了更多的内联或非内联成员函数,也不会改变单个类实例所占用的内存大小。
    ——
    但注意的是当要计算一个类的大小的时候,并不是直接通过查看类中成员的类型和个数,最终算出的所占字节决定的决定的!
    ——
  • 而是:成员在不同类型和个数影响大小的基础上引入了内存对齐

那内存对齐到底是什么?让我们接着往下看!

首先理解为什么要内存对齐

  1. 不是所有的硬件平台都能访问任意地址上的任意数据的:某些硬件平台只能在某些地址处取某些特定类型的数据,否则抛出硬件异常。(如取:int的4byte)
  2. 性能原因:因为假如在没有内存对齐的情况下:当一个类中刚好有两个成员:char 、int
    1. 此时不进行内存对齐,那么 char的1byte和int的4byte将会连在一起
    2. 假设要取其中的int,那么读取过程中从前往后的找int(每次读取4byte),但因为是char和int连着存放:
    3. 其中会有3byte和char连在一起(读取了前4byte,因为存在一些int,但其中第1byte并不是int的,也代表还没读取完)
    4. 所以还得继续读取还剩的1byte,那么就需要再一次进行读取,才能将int读完
    5. 也就代表需要读取两次才能将一个int读取完
    6. 但假如使用了内存对齐,将int对齐到倍数位置,就能很方便的不需要过滤char的,直接一次性读完
  3. 总体来说:结构体的内存对齐是拿空间来换取时间的做法

话不多说那么我们就快速的来看内存对齐的规则到底是什么,这么算出类对象大小


对齐规则

  • 首先我们理解对于变量,他们都是放到栈区的:
  • 而栈区:其实可以把他想象成一个竖起来的数组!
  1. 第一个参数直接放入,对齐到偏移量为0的位置
  2. 从第二个成员变量开始要对齐到偏移量为自身对齐数的整数倍
    1. 自身对齐数 = 判断自身大小 和 系统默认对齐数 进行比较,取较小值为对齐数(有点抽象先看着后面有例子!)
  3. 结构体的总大小:最终要为所有成员变量中的取过的最大对齐数的整数倍
  4. 如果有镶嵌结构体
    1. 那这个最大对齐数的判断也要包括所镶嵌的结构体 内的 成员的对齐数
    2. 并且这个镶嵌结构体也要对齐到自身的最大的对齐数上(在外部的结构体内)
  5. 附:在Linux gcc 环境下没有默认对齐数 对齐数就是其本身大小、计算偏移量的宏offsetof(类名,成员名)

例子结构如下:

struct/class S1
{char c1;int i;char c2;
};

分析:

  1. 首先将 c1(1byte) 直接放到 0 偏移量处,并占1byte
  2. 从第二个开始就要把成员,放到 自身对齐数的整数倍处!
    1. 也就是 i (int)放到自身对齐数整数倍处:自身对齐数 = 4 (取 自身大小4 和 默认对齐数8 的较小值)
    2. 那么从 就要放到 3 偏移处(从0开始:0 ~ 3 = 4),并占4byte(此时总大小就是 0 ~ 3 + 4 = 8)
    3. 在放一个 c2 ,对齐数为 1(1 > 8),此时总大小就占了9byte了
  3. 最终的大小等于:在成员中自身对齐数最大的数4的整数倍( 1 4 1)
  4. 所以还得让总大小值是4它的倍数:9 - > 12大小
    栈的存储过程图:
    在这里插入图片描述
struct name
{int a;char b;int c;int d;
};

4 + 1 + 3(偏移)+ 4 + 4 = 16
在这里插入图片描述

扩充:考虑多态情况下的:虚表指针

不仅要考虑内存对齐,在多态情形中我们还需要考虑虚表地址(它存储着类中所有的虚函数地址)

当一个类有虚函数时,在这个类中不仅仅需要考虑类成员的内存对齐以及 还要加上一个虚表地址大小(4byte/8byte(32位/64位(地址总线的宽度)))
在这里插入图片描述


本章完。预知后事如何,暂听下回分解。

如果有任何问题欢迎讨论哈!

如果觉得这篇文章对你有所帮助的话点点赞吧!

持续更新大量C++细致内容,早关注不迷路。

相关文章:

【C/C++】如何求出类对象的大小----类结构中的内存对齐

每日激励:“不设限和自我肯定的心态:I can do all things。 — Stephen Curry” 绪论​: 通过本章你能具体的了解到,如何计算出一个类的大小,并且了解其中到底是如何算的以及了解到为什么需要内存对齐这种算&#xff0…...

Linux:动静态库

1.库是什么,作用是什么 库是写好的,现有的可以复用的代码。现实中每个程序都要依赖很多基础的底层库,不可能每个人的代码都从零开始。 本质上来说库是一种可执行代码的二进制形式,可以被操作系统载入内存中执行。库有两种&#…...

鸿蒙跨平台框架ArkUI-X

01 引言 目前,移动端主流跨平台方案有Flutter、React Native、uni-app等等,还有刚推出不久的Compose-Multiplatform,真所谓是百花齐放。这些框架各有特点,技术实现各有差异,比如Flutter通过Dart编写的UI描述对接Flutte…...

第7章 wireshark(网络安全防御实战--蓝军武器库)

网络安全防御实战--蓝军武器库是2020年出版的,已经过去3年时间了,最近利用闲暇时间,抓紧吸收,总的来说,第7章开始学习抓包工具wireshark,如果你怀疑自己的电脑中毒了,那么用wireshark可以很轻松…...

【AI】神经网络|机器学习——图解Transformer(完整版)

Transformer是一种基于注意力机制的序列模型,最初由Google的研究团队提出并应用于机器翻译任务。与传统的循环神经网络(RNN)和卷积神经网络(CNN)不同,Transformer仅使用自注意力机制(self-attention)来处理输入序列和输出序列,因此可以并行计算,极大地提高了计算效率…...

002-SpringCloud-OpenFeign(远程调用)

SpringCloud-OpenFeign 1.引入依赖2.编写一个远程调用接口3.测试 1.引入依赖 <dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-openfeign</artifactId> </dependency><dependencyManageme…...

基于类型的声明接收props

在 Vue 3 中&#xff0c;除了运行时声明这种常见方式&#xff0c;还可以通过基于类型的声明、解构赋值等方式来接收 props&#xff0c;下面为你详细介绍&#xff1a; 1. 基于类型的声明 这种方式借助 TypeScript 的类型系统来定义 props&#xff0c;具有类型检查和代码提示的…...

多方安全计算(MPC)电子拍卖系统

目录 一、前言二、多方安全计算(MPC)与电子拍卖系统概述2.1 多方安全计算(MPC)的基本概念2.2 电子拍卖系统背景与需求三、MPC电子拍卖系统设计原理3.1 系统总体架构3.2 电子拍卖中的安全协议3.3 数学与算法证明四、数据加解密模块设计五、GPU加速与系统性能优化六、GUI设计与系…...

使用QT + 文件IO + 鼠标拖拽事件 + 线程 ,实现大文件的传输

第一题、使用qss&#xff0c;通过线程&#xff0c;使进度条自己动起来 mythread.h #ifndef MYTHREAD_H #define MYTHREAD_H#include <QObject> #include <QThread> #include <QDebug>class mythread : public QThread {Q_OBJECT public:mythread(QObject* …...

【无人机路径规划】基于麻雀搜索算法(SSA)的无人机路径规划(Matlab)

效果一览 代码获取私信博主基于麻雀搜索算法&#xff08;SSA&#xff09;的无人机路径规划&#xff08;Matlab&#xff09; 一、算法背景与核心思想 麻雀搜索算法&#xff08;Sparrow Search Algorithm, SSA&#xff09;是一种受麻雀群体觅食行为启发的元启发式算法&#xff0…...

基于物联网技术的分布式光伏监控系统设计与实现

一、分布式光伏发电系统标准规范 1.常见应用场景 2.并网标准 Q/GDW1480-2015《分布式电源接入电网技术规定》 分布式电源并网电压等级可根据各并网点装机容量进行初步选择&#xff0c;推荐如下&#xff1a; 8kW 及以下可接入220V&#xff1b; 8kW~400kW可接入380V&#xf…...

阿里发布新开源视频生成模型Wan-Video,支持文生图和图生图,最低6G就能跑,ComFyUI可用!

Wan-Video 模型介绍&#xff1a;包括 Wan-Video-1.3B-T2V 和 Wan-Video-14B-T2V 两个版本&#xff0c;分别支持文本到视频&#xff08;T2V&#xff09;和图像到视频&#xff08;I2V&#xff09;生成。14B 版本需要更高的 VRAM 配置。 Wan2.1 是一套全面开放的视频基础模型&…...

27. Harmonyos Next仿uv-ui 组件NumberBox 步进器组件禁用状态

温馨提示&#xff1a;本篇博客的详细代码已发布到 git : https://gitcode.com/nutpi/HarmonyosNext 可以下载运行哦&#xff01; 文章目录 1. 组件介绍2. 效果展示3. 禁用状态设置3.1 整体禁用3.2 输入框禁用3.3 长按禁用 4. 完整示例代码5. 知识点讲解5.1 禁用状态属性5.2 禁用…...

【软件工程】一篇入门UML建模图(状态图、活动图、构件图、部署图)

&#x1f308; 个人主页&#xff1a;十二月的猫-CSDN博客 &#x1f525; 系列专栏&#xff1a; &#x1f3c0;软件开发必练内功_十二月的猫的博客-CSDN博客 &#x1f4aa;&#x1f3fb; 十二月的寒冬阻挡不了春天的脚步&#xff0c;十二点的黑夜遮蔽不住黎明的曙光 目录 1. 前…...

AI智能导航站HTML5自适应源码帝国cms7.5模板

源码名称&#xff1a;AI导航站HTML5自适应源码帝国cms7.5模板 开发环境&#xff1a;帝国cms 7.5 安装环境&#xff1a;phpmysql var code "4d33ef8e-9e38-43b9-b37b-38f75944ecc9" 带软件采集&#xff0c;可以挂着自动采集发布&#xff0c;无需人工操作&#xff0…...

Redis 发布订阅模式详解:实现高效的消息通信

目录 引言 1. 什么是 Redis 发布订阅模式&#xff1f; 1.1 定义 1.2 核心概念 2. Redis 发布订阅的工作原理 2.1 基本流程 2.2 示例 2.3 频道与模式订阅 3. Redis 发布订阅的使用场景 3.1 实时消息通知 3.2 事件驱动架构 3.3 日志收集与分发 3.4 分布式锁与协调 4…...

ES的预置分词器

Elasticsearch&#xff08;简称 ES&#xff09;提供了多种预置的分词器&#xff08;Analyzer&#xff09;&#xff0c;用于对文本进行分词处理。分词器通常由字符过滤器&#xff08;Character Filters&#xff09;、分词器&#xff08;Tokenizer&#xff09;和词元过滤器&#…...

MPPT与PWM充电原理及区别详解

MPPT&#xff08;最大功率点跟踪&#xff09;和PWM&#xff08;脉宽调制&#xff09;是太阳能充电控制器中常用的两种技术&#xff0c;它们在原理、效率和适用场景上有显著区别。以下是两者的详细对比&#xff1a; 1. 工作原理 PWM&#xff08;脉宽调制&#xff09; 核心机制…...

【AGI】通往AGI的复兴号:模型工具演进与技术路径优化

通往AGI的复兴号&#xff1a;模型工具演进与技术路径优化 一、核心模型与工具技术指标及场景分析1. 边缘计算标杆&#xff1a;GLM-PC&#xff08;2024年11月&#xff09;2. 长文本处理王者&#xff1a;DeepSeek R1&#xff08;2025年1月&#xff09;3. 轻量化开源代表&#xff…...

java2025年常见设计模式面试题

1. 请解释建造者模式&#xff08;Builder Pattern&#xff09;及其应用场景。 答案&#xff1a; 建造者模式用于创建一个复杂的对象&#xff0c;同时允许用户只通过指定复杂对象的类型和内容就能构建它们&#xff0c;隐藏了复杂的构建逻辑。 示例&#xff1a; public class C…...

2025 后端自学UNIAPP【项目实战:旅游项目】6、我的收藏页面

代码框架视图 1、先添加一个获取收藏景点的列表请求 【在文件my_api.js文件中添加】 // 引入公共的请求封装 import http from ./my_http.js// 登录接口&#xff08;适配服务端返回 Token&#xff09; export const login async (code, avatar) > {const res await http…...

什么是EULA和DPA

文章目录 EULA&#xff08;End User License Agreement&#xff09;DPA&#xff08;Data Protection Agreement&#xff09;一、定义与背景二、核心内容三、法律效力与责任四、实际应用与意义 EULA&#xff08;End User License Agreement&#xff09; 定义&#xff1a; EULA即…...

自然语言处理——Transformer

自然语言处理——Transformer 自注意力机制多头注意力机制Transformer 虽然循环神经网络可以对具有序列特性的数据非常有效&#xff0c;它能挖掘数据中的时序信息以及语义信息&#xff0c;但是它有一个很大的缺陷——很难并行化。 我们可以考虑用CNN来替代RNN&#xff0c;但是…...

全面解析各类VPN技术:GRE、IPsec、L2TP、SSL与MPLS VPN对比

目录 引言 VPN技术概述 GRE VPN 3.1 GRE封装结构 3.2 GRE的应用场景 GRE over IPsec 4.1 GRE over IPsec封装结构 4.2 为什么使用GRE over IPsec&#xff1f; IPsec VPN 5.1 IPsec传输模式&#xff08;Transport Mode&#xff09; 5.2 IPsec隧道模式&#xff08;Tunne…...

用机器学习破解新能源领域的“弃风”难题

音乐发烧友深有体会&#xff0c;玩音乐的本质就是玩电网。火电声音偏暖&#xff0c;水电偏冷&#xff0c;风电偏空旷。至于太阳能发的电&#xff0c;则略显朦胧和单薄。 不知你是否有感觉&#xff0c;近两年家里的音响声音越来越冷&#xff0c;听起来越来越单薄&#xff1f; —…...

C++ 设计模式 《小明的奶茶加料风波》

&#x1f468;‍&#x1f393; 模式名称&#xff1a;装饰器模式&#xff08;Decorator Pattern&#xff09; &#x1f466; 小明最近上线了校园奶茶配送功能&#xff0c;业务火爆&#xff0c;大家都在加料&#xff1a; 有的同学要加波霸 &#x1f7e4;&#xff0c;有的要加椰果…...

从“安全密码”到测试体系:Gitee Test 赋能关键领域软件质量保障

关键领域软件测试的"安全密码"&#xff1a;Gitee Test如何破解行业痛点 在数字化浪潮席卷全球的今天&#xff0c;软件系统已成为国家关键领域的"神经中枢"。从国防军工到能源电力&#xff0c;从金融交易到交通管控&#xff0c;这些关乎国计民生的关键领域…...

系统掌握PyTorch:图解张量、Autograd、DataLoader、nn.Module与实战模型

本文较长&#xff0c;建议点赞收藏&#xff0c;以免遗失。更多AI大模型应用开发学习视频及资料&#xff0c;尽在聚客AI学院。 本文通过代码驱动的方式&#xff0c;系统讲解PyTorch核心概念和实战技巧&#xff0c;涵盖张量操作、自动微分、数据加载、模型构建和训练全流程&#…...

从实验室到产业:IndexTTS 在六大核心场景的落地实践

一、内容创作&#xff1a;重构数字内容生产范式 在短视频创作领域&#xff0c;IndexTTS 的语音克隆技术彻底改变了配音流程。B 站 UP 主通过 5 秒参考音频即可克隆出郭老师音色&#xff0c;生成的 “各位吴彦祖们大家好” 语音相似度达 97%&#xff0c;单条视频播放量突破百万…...

2.2.2 ASPICE的需求分析

ASPICE的需求分析是汽车软件开发过程中至关重要的一环&#xff0c;它涉及到对需求进行详细分析、验证和确认&#xff0c;以确保软件产品能够满足客户和用户的需求。在ASPICE中&#xff0c;需求分析的关键步骤包括&#xff1a; 需求细化&#xff1a;将从需求收集阶段获得的高层需…...