有什么不同? 指向数组与常规数组的指针

我熟悉Java并试图自学C / C ++。 我正在从一个托管他们材料的课程中窃取一些课程。 不幸的是,我不能问老师,因为我不在课堂上。 我关注的是“动态声明的数组”下的部分:

如果希望能够在运行时更改数组的大小,则声明动态数组。 这些都是通过指针和new运算符完成的。 有关指针的基础知识,请阅读指针部分。

使用new分配内存,然后以与静态数组相同的方式访问数组。 例如,

int * arrayPtr = new int [10]; for(int i = 0; i <10; i ++){arrayPtr [i] = i; }

内存画面与静态数组相同,但您可以根据需要更改大小。 不要忘记在分配新内存之前必须释放内存(否则会导致内存泄漏)。

delete [] arrayPtr; //删除数组指针时需要[] arrayPtr = new int [50]; 。 。 。

完成数组后,必须删除其内存:

delete [] arrayPtr;

动态多维数组以与Java类似的方式完成。 你将有指针指针。 例如,请参阅a

我的理解是C中的数组只是对数组中第一个元素的内存地址的引用。

那么, int *pointerArray = new int[10];之间的区别是什么int *pointerArray = new int[10];int array[10]; 如果有的话?

我做了一些测试,似乎表明他们完全一样。 网站是错的还是我读错了?

 #include  #include  using namespace std; int main(int argc, char** argv) { // Initialize the pointer array int *pointerArray = new int[10]; for (int i = 0; i < 10; i++){ pointerArray[i] = i; } // Initialize the regular array int array[10]; for (int i = 0; i < 10; i++){ array[i]= i; } cout << *(pointerArray + 5) << endl; cout << *(array + 5) << endl; cout << pointerArray[5] << endl; cout << array[5] << endl; cout << pointerArray << endl; cout << array << endl; return 0; } 

输出:

 5 5 5 5 0x8f94030 0xbfa6a37c 

我已经尝试按照网站上的描述“动态地重新调整”我的指针数组的大小,但是我的新(更大)指针数组最终填充了0,这不是很有用。

int array[10]; 静态声明数组大小,这意味着它是固定的 – 这是唯一的主要区别。 它也可能被分配在函数的堆栈框架内,即在程序的堆栈中。 您不必担心在这种数组上使用delete [] ,事实上,如果您delete它,可能会使程序崩溃。

当您使用operator new ,您会动态分配内存,这可能会更慢 ,内存通常来自而不是程序的堆栈(尽管并非总是如此)。 在大多数情况下这是更好的,因为堆栈空间比堆空间更有限。 但是,您必须注意内存泄漏并在不再需要时delete[]您的内容。

至于你的数组被零填充,你的课程材料没有说的是你必须这样做:

 int *arr = new int[20]; // old array //do magic here and decide that we need a bigger array int *bigger = new int[50]; // allocate a bigger array for (int i = 0; i < 20; i++) bigger[i] = arr[i]; // copy the elements from the old array into the new array delete[] arr; arr = bigger; 

该代码将数组arr扩展了30多个元素。 请注意,您必须将旧数据复制到新数组中,否则它将不存在(在您的情况下,所有内容都变为0)。

我的理解是C中的数组只是对数组中第一个元素的内存地址的引用。

那么,int * pointerArray = new int [10]之间的区别是什么? 和int数组[10]; 如果有的话?

你提到的是在任何C / C ++初学者中引起很多混淆的原因。

在C / C ++中,数组对应的存储块足够大以容纳其所有元素。 这与[]语法相关联,如您的示例中所示:

 int array[10]; 

C / C ++的一个特性是你可以通过使用指向其类型的指针来引用数组。 因此,您可以写:

 int* array_pointer = array; 

这与:

 int* array_pointer = &array[0]; 

这允许以通常的方式访问数组元素: array_pointer[3] ,但你不能将array视为指针,就像在它上面做指针算术(即数组++悲惨地失败)。

也就是说,你可以在不使用[]语法的情况下管理数组,只需使用malloc分配数组,然后将它们与原始指针一起使用即可。 这就是C / C ++的“美”。

恢复:必须区分指针和它指向的内存(实际数组):

  1. 声明中的[]语法(即int array[10]; )同时引用这两个方面(它给出了一个指针和一个数组);

  2. 当声明一个指针变量(即int* p; )时,你只需得到指针;

  3. 在计算表达式时(即int i = p[4];array[4]; ), []仅表示解除引用指针。

除此之外, int *pointerArray = new int[10];之间的唯一区别int *pointerArray = new int[10];int array[10]; 是前者是动态分配的,后者是堆栈。

动态分配:

 int * pointerArray = new int[10]; 

[顺便说一下,这是一个指向10个整数数组的指针,而不是一个指针数组]

静态分配(可能在堆栈上):

 int array[10]; 

否则他们是一样的。

来自Java时理解C / C ++数组的问题是C / C ++区分数组变量和用于存储数组内容的内存。 这两个概念都很重要且不同。 在Java中,您实际上只是对一个数组对象的引用。

您还需要了解C / C ++有两种分配内存的方法。 可以在帮助或堆栈上分配内存。 Java没有这种区别。

在C和C ++中,数组变量是指向数组第一个元素的指针。 数组变量可以存在于堆或堆栈上,包含其内容的内存也可以存在。 他们可能是不同的。 您的示例是int数组,因此您可以将数组变量视为int*

int *pointerArray = new int[10];int array[10];

第一个区别是包含第一个数组内容的内存在堆上分配。 第二个arrays更棘手。 如果array是函数中的局部变量,那么它的内容将在堆栈上分配,但如果它是类的成员变量,则在分配包含对象(堆栈或堆栈)的任何位置分配其内容。

第二个区别是,正如您所知,第一个数组是动态的:它的大小可以在运行时确定。 第二个数组是固定的:编译器必须能够在编译时确定其大小。

首先,我会寻找其他一些学习C ++的地方。 您引用的页面非常混乱,与实际使用C ++编程的方式几乎没有关系。 在C ++中,大多数情况下,您将std::vector用于数组,而不是您引用的页面上提出的复杂解决方案。 实际上,您从不使用operator new[] (数组new )。

实际上, std::vector在某些方面比Java中的简单数组更像ArrayList ; 与Java中的数组不同,您可以通过在其中插入元素来简单地增长矢量,最好是在最后。 它支持迭代器,尽管C ++迭代器与Java迭代器有很大不同。 另一方面,您可以使用[]运算符访问它,就像普通数组一样。

您引用的页面上描述的数组通常称为C样式数组。 在C ++中,它们的使用主要限于具有静态生命周期的对象,尽管它们偶尔会出现在类中。 无论如何,它们永远不会动态分配。

主要区别在于数组上不允许指针允许的某些操作。

一方面:

 int ar[10]; 

正在使用堆栈上分配的内存。 您可以将其视为本地可用,并且可以将指针/引用传递给其他函数,一旦内存超出范围,内存将被释放(在主示例结尾的示例中,但通常是不是这样)。

另一方面:

 int ar* = new int[10]; 

为堆上的数组分配内存。 它可用,直到您的整个程序退出或使用它删除

 delete[] ar; 

请注意,对于删除,您需要“[]”当且仅当相应的新用户也拥有它们时。

你指出的区域有区别,但没有区别。 *pointerArray将指向大小为10个字节的内存块的开头。 array 。 唯一的区别是它存储在内存中的位置。 pointerArray是动态分配的内存(在run-time ),因此将进入堆,而array[10]将在compile-time分配并将进入堆栈。

确实,您可以通过使用指向其第一个元素的指针来获得大多数数组function。 但是编译器知道静态数组由几个元素组成,最显着的区别是sizeof运算符的结果。

sizeof(pointerArray) = sizeof int*

sizeof(array) = 10 * sizeof int