C++類成員內存分布詳解

本文將探討C++類中成員變量的內存分布情況,包括普通成員、靜態成員、虛函數等不同情況下的內存布局。


一、基本成員內存布局

1. 普通成員變量

普通成員變量按照聲明順序在內存中連續排列(受訪問修飾符和內存對齊影響):

class NormalClass {
public:int a;      // 4字節char b;     // 4字節(考慮int對齊)double c;   // 8字節char d;     // 8字節(考慮double 對齊)
};
// sizeof(NormalClass) = 24 (考慮對齊填充)

內存布局:

| 0-3: int a | 4: char b | 5-7: padding | 8-15: double c | 16: char d | 17-23: padding |

2. 帶繼承的內存布局

派生類的成員追加在基類成員之后:

class Base {
public:int base_var; // 4字節
};class Derived : public Base {
public:int derived_var; // 4字節,再加上Base 類的 4字節,總共8字節
};

內存布局:

| 0-3: Base::base_var | 4-7: Derived::derived_var |

二、靜態成員的內存分布

靜態成員不占用類實例的內存空間,存儲在全局數據區

class WithStatic {
public:int normal_var;         // 占用實例空間static int static_var;  // 不占用實例空間
};
// sizeof(WithStatic) == sizeof(int)

三、虛函數對內存的影響

1. 含有虛函數的類

編譯器會隱式添加虛表指針(vptr),通常放在對象起始位置,虛函數表(vtable)本身不占用類實例的內存空間,vtable 存儲在程序的只讀數據段(全局靜態區),每個類(而非對象)共享一個 vtable。虛表指針(vptr)會占用類實例的內存空間,每個對象實例中存儲一個指向 vtable 的指針,在 64 位系統中占用 8 字節,32 位系統中占用 4 字節:

class WithVirtual {
public:virtual void foo() {}  // 添加vptrint a;
};
// 在32位系統上sizeof(WithVirtual) == 8 (vptr + int)
// 在64位系統上sizeof(WithVirtual) == 16 (vptr + int + padding)

內存布局(64位系統):

| 0-7: vptr | 8-11: int a | 12-15: padding |

2. 繼承體系中的虛函數

派生類與基類共享同一個vptr(單繼承情況下):

class BaseWithVirtual {
public:virtual void foo() {}int base_var;
};class DerivedVirtual : public BaseWithVirtual {
public:virtual void bar() {}  // 添加到虛表int derived_var;
};

內存布局(64位系統):

| 0-7: vptr | 8-11: Base::base_var | 12-15: Derived::derived_var |

四、多繼承的內存布局

多繼承情況下,每個基類子對象按聲明順序排列:

class Base1 { public: int base1_var; };
class Base2 { public: int base2_var; };class MultiDerived : public Base1, public Base2 {
public:int derived_var;
};

內存布局:

| 0-3: Base1::base1_var | 4-7: Base2::base2_var | 8-11: derived_var |

五、驗證內存布局的代碼

#include <iostream>
#include <cstddef>#define PRINT_OFFSET(className, member) \std::cout << "Offset of " #member ": " \<< offsetof(className, member) << std::endlstruct Test {virtual void foo() {}  // 添加vptrint a;char b;static int c;
};int main() {std::cout << "Sizeof Test: " << sizeof(Test) << std::endl;PRINT_OFFSET(Test, a);  // 64位系統輸出 8PRINT_OFFSET(Test, b);  // 64位系統輸出 12return 0;
}

總結表格

特性是否影響實例大小存儲位置
普通成員變量棧/堆
靜態成員變量全局數據區
虛函數是(添加vptr)虛表
繼承追加基類成員
虛繼承更復雜布局

注意事項

  1. 實際內存布局可能因編譯器實現不同而有所差異
  2. 使用 offsetof 宏驗證偏移量
  3. 內存對齊可通過 #pragma pack 指令調整

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/bicheng/76192.shtml
繁體地址,請注明出處:http://hk.pswp.cn/bicheng/76192.shtml
英文地址,請注明出處:http://en.pswp.cn/bicheng/76192.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

計算機視覺——為什么 mAP 是目標檢測的黃金標準

概述 在目標檢測領域&#xff0c;有一個指標被廣泛認為是衡量模型性能的“黃金標準”&#xff0c;它就是 mAP&#xff08;Mean Average Precision&#xff0c;平均精確率均值&#xff09;。如果你曾經接觸過目標檢測模型&#xff08;如 YOLO、Faster R-CNN 或 SSD&#xff09;…

C語言單鏈表的增刪改補

目錄 &#xff08;一&#xff09;單鏈表的結構定義及初始化 (二)單鏈表的尾插&#xff0c;頭插 (三)單鏈表的尾刪&#xff0c;頭刪 (四)單鏈表的查找&#xff0c;刪除&#xff0c;銷毀 單鏈表是數據結構課程里的第二個數據結構。單鏈表在邏輯結構是連續的&#xff0c;在物理…

Android10.0 framework第三方無源碼APP讀寫斷電后數據丟失問題解決

1.前言 在10.0中rom定制化開發中,在某些產品開發中,在某些情況下在App用FileOutputStream讀寫完畢后,突然斷電 會出現寫完的數據丟失的問題,接下來就需要分析下關于使用FileOutputStream讀寫數據的相關流程,來實現相關 功能 2.framework第三方無源碼APP讀寫斷電后數據丟…

殺戮尖塔(Slay The Spire) 的全新角色模組 - 女巫

女巫&#xff08;The Witch&#xff09; 殺戮尖塔&#xff08;Slay The Spire&#xff09; 的全新角色模組 女巫模組為游戲增添了超過 75 張新卡牌和 4 個全新遺物&#xff0c;圍繞 詛咒&#xff08;Curses&#xff09; 展開獨特的玩法體驗。她的起始遺物 黑貓&#xff08;Bl…

AI開發學習路線(闖關升級版)

以下是一份輕松版AI開發學習路線&#xff0c;用「闖關升級」的方式幫你從零開始變身AI開發者&#xff0c;每個階段都配有有趣的任務和實用資源&#xff0c;保證不枯燥、可落地&#xff01;&#x1f447; 目錄 &#x1f530; 新手村&#xff1a;打基礎&#xff08;1-2個月&…

迭代器模式深度解析與實戰案例

一、模式定義 迭代器模式&#xff08;Iterator Pattern&#xff09; 是一種行為設計模式&#xff0c;提供一種方法順序訪問聚合對象的元素&#xff0c;無需暴露其底層表示。核心思想是將遍歷邏輯從聚合對象中分離&#xff0c;實現 遍歷與存儲的解耦。 二、核心組件 組件作用…

SSH遠程工具

一、常見SSH遠程工具 工具開源跨平臺多標簽文件傳輸高級功能價格Xshell?Win????腳本、會話管理免費/商業版Tabby??全平臺????插件擴展免費MobaXterm?Win????集成工具集免費/付費SecureCRT?Win/macOS/Linux????企業級加密$129+PuTTY??全平臺??基礎連接…

VUE中的路由處理

1.引入,預處理main.ts import {} from vue-router import { createRouter, createWebHistory } from vue-router import HomePages from @/pages/HomePages.vue import AboutPage from @/pages/AboutPage.vue import NewsPage from @/pages/NewsPage.vue //1. 配置路由規…

編程助手fitten code使用說明(超詳細)(vscode)

這兩年 AI 發展迅猛&#xff0c;作為開發人員&#xff0c;我們總是追求更快、更高效的工作方式&#xff0c;AI 的出現可以說改變了很多人的編程方式。 AI 對我們來說就是一個可靠的編程助手&#xff0c;給我們提供了實時的建議和解決方&#xff0c;無論是快速修復錯誤、提升代…

Opencv計算機視覺編程攻略-第九節 描述和匹配興趣點

一般而言&#xff0c;如果一個物體在一幅圖像中被檢測到關鍵點&#xff0c;那么同一個物體在其他圖像中也會檢測到同一個關鍵點。圖像匹配是關鍵點的常用功能之一&#xff0c;它的作用包括關聯同一場景的兩幅圖像、檢測圖像中事物的發生地點等等。 1.局部模板匹配 憑單個像素就…

C++內存管理優化實戰:提升應用性能與效率

&#x1f9d1; 博主簡介&#xff1a;CSDN博客專家、CSDN平臺優質創作者&#xff0c;高級開發工程師&#xff0c;數學專業&#xff0c;擁有高級工程師證書&#xff1b;擅長C/C、C#等開發語言&#xff0c;熟悉Java常用開發技術&#xff0c;能熟練應用常用數據庫SQL server,Oracle…

17-產品經理-創建發布

點擊“發布”-“創建發布”。 填寫發布名稱&#xff0c;選擇測試的版本。還可以設置此次發布是否為“里程碑”。 點擊“保存”后&#xff0c;進入該發布詳情頁面。需要為此次發布關聯需求、已解決BUG、以及遺留BUG。可以通過設置條件&#xff0c;進行“搜索”&#xff0c;然后批…

Axure RP9.0教程 | 內聯框架 對應html 元素中的iframe標簽 (打開內部頁面和外部網址)

文章目錄 引言I 打開內部頁面II 打開外部網址操作效果引言 應用場景: 選擇右側不同欄目,左側內容發生變化 I 打開內部頁面 在公用元件庫中找到內聯框架圖標,將其拖到畫布中,設置其寬、高;在右側添加三個按鈕,分別用來跳轉三個不同的頁面;在內部框架中,添加三個子頁面,…

在1panel中安裝WebUI

如果需要建站&#xff0c;那得選安裝Openresty。點擊應用商店&#xff0c;安裝 Openresty 接下來安裝Ollama&#xff0c;可以部署本地模型提供給WebUi平臺使用 最后是安裝 WebUi&#xff0c;安裝時需要填寫Ollama的地址: 容器地址&#xff1a;30000 這些安裝都很方便&#xf…

項目難點亮點

Vue項目 RBAC設計 用戶權限設置 WebSocket 消息處理 BPMN擴展 跨語言模型的調用 大片文件(影像,模型等,數據-模型集成) 組件&指令封裝 低代碼表單構建、BPMN編輯器集成與實現 通用參考點 若依(RuoYi)是一個基于 Vue.js 和 Spring Boot 的前后端分離權限管理系…

JVM生產環境調優實戰

案例三&#xff1a;JVM頻繁Full GC優化 1. 項目背景&#xff08;Situation&#xff09; 在云中萬維跨境支付的反洗錢系統中&#xff0c;我們負責對海量交易數據進行實時規則校驗&#xff0c;以確保符合監管要求。系統日均處理交易量超過500萬筆&#xff0c;峰值QPS達到3000&a…

ASP.NET Web 中進行 GET/POST 提交并接收返回數據的幾種方案

在 ASP.NET Web 應用程序中進行 GET 請求并接收返回數據可以通過多種方式實現&#xff0c;以下是幾種常見的方法&#xff1a; 1. 使用 WebClient 類&#xff08;簡單方式&#xff09; using System.Net; using System.IO;public string GetDataFromUrl(string url) {using (W…

Springboot--Kafka客戶端參數關鍵參數的調整方法

調整 Kafka 客戶端參數需結合生產者、消費者和 Broker 的配置&#xff0c;以實現性能優化、可靠性保障或資源限制。以下是關鍵參數的調整方法和注意事項&#xff1a; 一、生產者參數調整 ?max.request.size? ?作用?&#xff1a;限制單個請求的最大字節數&#xff08;包括消…

Android學習總結之service篇

引言 在 Android 開發里&#xff0c;Service 與 IntentService 是非常關鍵的組件&#xff0c;它們能夠讓應用在后臺開展長時間運行的操作。不過&#xff0c;很多開發者僅僅停留在使用這兩個組件的層面&#xff0c;對其內部的源碼實現了解甚少。本文將深入剖析 Service 和 Inte…

ExternalProject_Add 使用手冊與文檔詳解

一、基本概念與語法 ExternalProject_Add 是 CMake 的一個核心命令&#xff0c;用于在構建過程中集成和管理外部項目&#xff08;如第三方庫&#xff09;。它支持完整的生命周期管理&#xff0c;包括下載、配置、構建、安裝和測試。 語法&#xff1a; ExternalProject_Add(&l…