内存分配是如何在C 中发生的

How Memory allocation Happen in c++

本文关键字:分配 内存      更新时间:2023-10-16

我是C 的新手,并且是尝试使用功能打印数组的练习。我创建了两个数组arrarr2如下。

int main(){
int arr[5] = {11, 12, 13, 14, 15};
int i =1;
int* arr2 = &i;
*arr2 =1;
*(arr2+1) =2;
*(arr2+2) =3;
*(arr2+3) =4;
*(arr2+4) =5;
printArray(arr2,5);    
printArray(arr,5);
}

我正在尝试使用下面的功能打印这两个阵列。

void printArray(int arr[],int size){
   for(int i=0; i<size; i++){       
      cout<<*(arr+i)<<" ";
   }
   cout<<endl;
}

运行程序后的结果是

 1 2 3 4 5
 2 3 4 5 15

,但预期的结果是

1 2 3 4 5
11 12 13 14 15

有人可以解释这里正在发生的事情,如果您可以使用适当的图表解释内存分配的问题。

您声明的变量在堆栈上声明:

int arr[5] = { 11, 12, 13, 14, 15 }; // 5xsizeof (int) bytes
int i = 1; // sizeof (int) bytes on the stack
int *arr2 = &i; // sizeof (void*) bytes on the stack

现在arr2是指向int的指针。在另一种情况下,它可能是一个动态分配的数组的指针,但这不是:它指向i在堆栈上的位置。当您这样做时:

*(arr2 + 1) = 2;

您将2分配给堆栈上的另一个地址(&i之后的一个地址),从您的结果中,它看起来与arr[0]的地址相吻合,这有点逻辑(但既然它是不确定的行为,一切可能发生)。

由于您要分配给堆栈上的地址,因此您没有得到segfault,但是您会损坏堆栈,这比获得segfault要差得多:

  • segfault是一个明确的信号,告诉您您正在尝试非法内存访问。您知道它发生在哪里,您可以修复它。
  • 堆栈腐败会静静地发生,直到该程序崩溃为止,这可能在任何地方发生。这是未发现的"非法"内存访问的结果,因为堆栈已经为您的程序保留。当然,调试非常困难,因为崩溃可能发生在与故障代码完全无关的地方。

arr2不是数组。它是int i的指针。您正在从内存中阅读不是您的记忆。

而是使用:

int* arr2 = new int[how_long_array_you_want]

不要忘记删除arr2

哇没有sigsegv?只是概况的组合,可能(在计算机内)我在数组之前被声明的变量。所以你不能做。变量" i"只是为整数分配一个插槽。但是您需要5.(ARR2 1)时,您将在不贡献的邻居随机变量中写入。在这种情况下,大概是ARR []。幸运的是,整数也是一个整数,否则您将获得Sigsegv错误因此代码将为

int i[5];
int *arr2=i;

所以它有效