C++ 中的全局变量是存储在堆栈、堆还是两者都不存储?

Posted

技术标签:

【中文标题】C++ 中的全局变量是存储在堆栈、堆还是两者都不存储?【英文标题】:Are global variables in C++ stored on the stack, heap or neither of them? 【发布时间】:2017-11-05 16:42:48 【问题描述】:

一开始我很确定正确的答案必须是“都不是”,因为全局变量存储在数据存储器中,但后来我找到了 Robert Lafore 的这本书,名为“C++ 中的面向对象编程” " 并且它明确指出,根据 C++ 标准,全局变量存储在堆上。现在我很困惑,无法真正弄清楚所提问题的正确答案是什么。

为什么全局变量会存储在堆上?我错过了什么?

编辑:Link to the book - 第 231 页

【问题讨论】:

" 并且它清楚地指出,根据 C++ 标准,全局变量存储在堆上" - 我真的怀疑它是否清楚地说明了这一点。贴出相关文字。 @NeilButterworth 我已经编辑了问题并添加了本书的链接,如果你想在那里查找的话。无论如何,它说 “如果您熟悉操作系统架构,您可能有兴趣知道局部变量和函数参数存储在堆栈上,而全局和静态变量存储在堆上。”我> 书错了。它们不存储在堆上。它们存储在数据段或 .bss 段中。 嗯,这当然不是真的。 C++ 没有明确说明它们的存储位置,但我知道没有实现将它们存储在堆上。 好的,谢谢你们的帮助。这真的让我很困惑。 【参考方案1】:

这本书在第 205 页是这样说的:

如果您熟悉操作系统架构,您可能有兴趣知道局部变量和函数参数存储在堆栈中,而全局变量和静态变量存储在堆中。

这绝对是书中的错误。首先,应该从存储时长的角度来讨论存储,就像 C++ 标准所做的那样:“堆栈”是指自动存储时长,而“堆”是指动态存储时长。 “堆栈”和“堆”都是分配策略,通常用于实现具有各自存储时长的对象。

全局变量具有静态存储期限。它们存储在与“堆”和“堆栈”分开的区域中。全局常量对象通常存放在“代码”段中,而非常量全局对象存放在“数据”段中。

【讨论】:

"Stack" 和 "heap" 肯定与存储时长有关,但事实并非如此。栈是一种适用于具有自动存储时长的对象的分配策略,而堆是一种适用于具有动态存储时长的对象的分配策略。 (当然,两者都不是真正适合具有静态存储持续时间的对象。) 我知道这对 elf 格式有效,但对其他格式也有效吗? @AdrianRK 你的意思是“数据”和“代码”段?大多数格式都有用于类似目的的段,尽管名称通常不同(例如,“代码”段通常称为“文本”段)。 许多 C 工具链有两个用于全局变量的部分:一个(在 Unix 领域传统上称为“数据”)用于具有编译时常量初始值设定项的全局变量,另一个(传统上称为“BSS” ) 用于在运行时初始化的全局变量。可执行文件包含“数据”段中变量的实际初始值,但对于 BSS,它只需要说明它的大小。 @DarsenLu 甚至非常量的全局和静态对象(与全局相同,但名称可见性降低)也存储在堆栈之外。这就是为什么你的全局变量没有溢出堆栈。

以上是关于C++ 中的全局变量是存储在堆栈、堆还是两者都不存储?的主要内容,如果未能解决你的问题,请参考以下文章

堆的Java和堆栈是否都驻留在RAM中,类似于C ++?

c++中数组和对象的数据是存储在栈内存还是堆内存?

C++ STL 内存管理:堆栈还是堆?

进程的虚拟地址空间,堆栈堆数据段代码段

C/C++程序中全局变量局部变量堆栈的存储区域介绍

通用列表是存储在 C# 中的堆栈还是堆中?