【问题标题】:How does it work in memory with pointers and in general?它如何在内存中使用指针以及一般情况下工作?
【发布时间】:2012-12-24 06:31:24
【问题描述】:

假设我有一个指向 C++ 中的 int 的指针。

int i = 1;
int* myInt = &i;

myInt中,我有内存位置的信息来获取实际的整数值。我猜myInt中的信息必须存储在内存中。

但是编译器如何知道myInt 在内存中的位置?我想它必须将myInt 的地址保存在内存中。但是它把最后的信息保存在哪里呢? Memoryinception?

这更像是一个关于如何管理内存的一般问题。

【问题讨论】:

    标签: c++ pointers memory


    【解决方案1】:

    编译器知道 myInt 在哪里,因为它将它放在首位。在编译期间,一个名为symbol table 的数据结构用于跟踪这些位置。编译代码只包含地址而不包含变量名(或lexical names)。

    【讨论】:

    • Nitpick:全局标识符的符号表在运行时用于动态链接目的。
    【解决方案2】:

    每个变量都有自己的内存地址,不管它包含什么。因此,当您存储一个指向整数的指针时,您只是存储了一个指向变量数据的地址。这个地址容器也有一个地址。您可以通过制作指向指针的指针并以您满意的方式显示它们来进行实验:

    int i = 1;
    int* pointer = &i;
    cout << "address1:[" << &i << "] address2:[" << &pointer << "]\n";
    

    【讨论】:

    • 但是什么时候停止呢?在您的示例中,指针具有由 &pointer 定义的地址。该地址必须存储在内存中。要知道该地址的存储位置,我需要一个也必须存储的内存地址。等
    • 是的,只要您创建指向变量的指针,它就会像这样继续下去,可能是无限的。但是在您专门创建一个新的指针变量之前,这种链接不会发生。否则,地址只是写在内存堆栈上的地址,就像街道上的地址一样。
    • 一旦您将该指针地址分配给一个变量进行存储,那么您将自动创建一个新变量(恰好存储一个地址),该变量具有自己的地址和内存大小。
    【解决方案3】:

    每个变量都有一个地址。

    全局变量和静态变量相对于“加载器”放置在内存中的整个模块进行寻址。加载程序读取“模块重定位表”,其中包含代码中应更正地址的位置,并更正这些位置。 Google:也可以定位独立代码。

    自动变量(在函数体中声明)相对于激活记录进行寻址。每次调用函数时,都会将激活记录压入堆栈,这是所有自动变量的“结构”。激活记录的地址存储在硬件寄存器中,用于寻址各个变量。

    【讨论】:

      【解决方案4】:

      包括指针在内的所有局部变量都存储在堆栈中。编译后的代码使用堆栈指针相对寻址来访问它们。所以你的第一个变量将位于 0+sp,你的第二个变量的大小为第一个变量 + sp 等等。

      【讨论】:

        【解决方案5】:

        i 的实际地址以及myInt 的实际地址直接嵌入到机器代码、访问i 的实际机器命令和访问myInt 的实际机器命令中。

        这些最终地址不存储在数据存储中。相反,它们直接嵌入到通过 CPU 的机器命令流中。它们被称为“立即操作数”。 CPU 接收这些地址以及实际的机器命令,因此 CPU 不必从数据存储器中的其他位置检索它们。

        这就是这个看似“无限”的递归停止的方式。这就是它触底的方式。

        对于全局变量,确切的地址在编译时就知道了,并直接嵌入到机器命令中。对于局部变量,当前栈帧中的地址偏移量在编译时是已知的,直接嵌入到机器命令中。

        【讨论】:

          猜你喜欢
          • 2017-07-09
          • 2021-11-13
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2013-01-26
          • 1970-01-01
          相关资源
          最近更新 更多