【问题标题】:Where are the variable/reference names or types stored in memory for stack/heap variables?堆栈/堆变量在内存中存储的变量/引用名称或类型在哪里?
【发布时间】:2015-01-24 13:23:25
【问题描述】:

我想我理解堆栈和堆之间的主要区别。

在下面的程序中,在堆上创建了一个大小为 n 的对象。在堆栈上创建了一个指向这个 sofar 无名对象的指针 p,它占用 4 个字节(至少在我的系统上)。如果我理解得很好,因为引用不使用额外的内存,所以不会分配更多的内存(除了 main() 在堆栈上返回的 int 之外)。

Class Object;  // n bytes

int main() {
    Object* p = new Object();
    Object& r = *p;
    // ...
}

不过,内存管理还不完全清楚:

1) 名称 p 和 r 存储在哪里?它们都是本地名称,所以我想它们也应该放在堆栈上?这不需要额外的内存来存储变量名和它所引用的内存部分之间的绑定吗?

2) 指针的类型存储在哪里?指针在堆栈上仅占用 4 个字节,(我认为)这是存储内存地址的确切大小。计算机如何知道在该地址可以找到哪种类型?

3) 与 (2) 类似,堆上的对象需要 n 个字节的存储空间,并且对它的唯一(直接)引用需要 0 个字节。这个对象的类型存储在哪里,所以在使用r的时候就知道是什么类型了吗?

4) 我知道编译后的程序也驻留在内存中的某个地方以指导它的执行。这是在堆栈还是堆上,还是这仍然是内存的另一部分?

【问题讨论】:

  • 您想知道p*p 的类型吗?因为对于派生类,p 也可以指向更大对象内的基类子对象。

标签: c++ memory heap-memory stack-memory variable-names


【解决方案1】:

名称 p 和 r 存储在哪里?

它们不是——变量名是静态的,在运行时不可用。编译器知道变量将存储在哪里,并生成代码来访问该内存位置,而无需任何名称。

它们可能在程序文件的特殊调试部分中可用,以允许调试器显示变量的值。

指针的类型存储在哪里?

它不是——类型也是静态的(除了与多态类类型相关的有限动态类型信息,但不是指针类型)。编译器知道类型,并生成代码以针对该类型以正确的方式访问存储的值。

这个对象的类型存储在哪里?

如果类型是多态(即如果是至少有一个虚函数的类类型),那么会有一些静态数据,存放在一个你不能直接访问的未指定的地方, 来描述类型。将有足够的数据来支持虚函数调用(通常是指向最终覆盖的指针表)和 RTTI(dynamic_cast 使用的继承结构规范,type_info 结构可通过typeid 获得)。

否则,所有类型信息都是静态的。

[编译后的程序]是在栈上还是在堆上,还是这还是内存的另一部分?

在典型的计算机上,它位于静态内存中(代码文本部分),在程序启动时加载。在嵌入式系统上,它可能会更永久地位于只读内存中。

【讨论】:

  • 嗯,有 RTTI - 运行时类型信息,因为并非所有类型都是完全静态的。 OO 允许多态性。但是指针本身永远不会是多态的。
  • @MSalters:确实,我有些过于简单化了。
  • 重读时,我认为这个问题本身就是模棱两可的。它还想知道“在那个地址可以找到哪种类型?”,即它肯定想知道指向的对象。然后 RTTI 绝对是相关的。我们不知道Object 是否是多态的。
  • @MSalters:很好,也许问题 3 需要自己的答案。
【解决方案2】:

由于引用不使用额外内存,因此不会分配更多内存

C++ 标准中没有指定如何实现引用,但大多数编译器会像指针一样实现它们,因此在未优化的代码中,r 可能还有另外 4 个字节(在您的系统上)。

名称 p 和 r 存储在哪里

这里存储的指针的类型是什么?

[r] 的类型存储在哪里

它们在编译器运行时存在于编译器本身内部,并且可能存在于放入生成的对象/库/程序中的一些调试符号信息中,以帮助交互式调试,例如GCC 的 g++ -g 选项,但它们不能通过普通 C++ 程序语句存储或访问。

我知道编译后的程序也驻留在内存中的某个地方以指导它的执行。这是在堆栈上还是在堆上,还是这仍然是内存的另一部分?

编译后的程序是一堆二进制数据和机器码操作码(数字),操作系统知道如何加载并要求 CPU 解释和执行。该数据通常不在堆栈或堆上,而是混合在操作系统安排的“未初始化数据”、“初始化数据”和“代码”段/区域中。

【讨论】:

    【解决方案3】:

    计算机永远不知道 p 和 r。 变量名用于提高高级语言的可读性。 例如,您可以通过

    获取汇编代码
    gcc -S -c code.c
    

    code.s中根本没有p和r

    【讨论】:

      猜你喜欢
      • 2015-05-27
      • 2014-04-21
      • 2016-09-08
      • 1970-01-01
      • 2011-03-01
      • 2018-08-27
      • 1970-01-01
      • 2014-02-11
      • 2015-03-09
      相关资源
      最近更新 更多