C ++中的静态数组与动态数组

时间:2010-04-20 02:03:40

标签: c++ dynamic arrays static allocation

C ++中静态数组和动态数组有什么区别?

我必须为我的班做一个作业,它说不要使用静态数组,只使用动态数组。我看过这本书和网上,但我似乎并不理解。

我认为静态是在编译时创建的,在运行时是动态的,但我可能会误认为是内存分配。

你能解释一下C ++中静态数组和动态数组之间的区别吗?

11 个答案:

答案 0 :(得分:83)

在堆栈上创建本地数组,并且具有自动存储持续时间 - 您不需要手动管理内存,但是当它们结束时它们会被销毁。它们必然具有固定的大小:

int foo[10];

使用operator new[]创建的数组具有动态存储持续时间并存储在堆上(技术上称为“免费存储”)。它们可以有任何大小,但你需要自己分配和释放它们,因为它们不属于堆栈框架:

int* foo = new int[10];
delete[] foo;

答案 1 :(得分:27)

static是C和C ++中的关键字,因此静态在应用于变量或数组时具有非常特定的含义,而不是一般描述性术语。为了加剧混乱,它在不同的背景下有三个不同的含义。因此,静态数组可以是固定的也可以是动态的。

让我解释一下:

第一个是C ++特定的:

  • 静态类成员是未使用构造函数实例化或使用析构函数删除的值。这意味着必须以其他方式初始化和维护成员。 static成员可以是初始化为null的指针,然后在第一次调用构造函数时进行分配。 (是的,这将是静态和动态的)

两个继承自C:

  • 在函数内,静态变量是在函数调用之间保留其内存位置的变量。它是静态的,因为它只被初始化一次并在函数调用之间保留它的值(使用静态使函数不可重入,即不是线程安全的)

  • 在函数外部声明的静态变量是全局变量,只能在同一模块中访问(源代码文件与任何其他#include一起)

我想问的问题是动态数组和固定数组或编译时数组之间的区别。这是一个更简单的问题,编译时数组是事先确定的(编译程序时)并且是函数堆栈帧的一部分。它们在main函数运行之前分配。动态数组在运行时使用“new”关键字(或来自C的malloc系列)进行分配,并且事先不知道它们的大小。在程序停止运行之前,动态分配不会自动清除。

答案 2 :(得分:11)

我认为你班上使用的语义令人困惑。 “静态”可能意味着什么只是“恒定大小”,而“动态”可能意味着“可变大小”。在那种情况下,一个恒定大小的数组可能如下所示:

int x[10];

和“动态”只是一种允许底层存储在运行时增加或减少的结构。大多数情况下,C ++标准库中的std::vector类就足够了。像这样使用它:

std::vector<int> x(10); // this starts with 10 elements, but the vector can be resized.

std::vector已定义operator[],因此您可以使用与数组相同的语义。

答案 3 :(得分:8)

静态数组在编译时分配内存,内存在堆栈上分配。然而,动态数组在运行时分配内存,内存从堆分配。

int arr[] = { 1, 3, 4 }; // static integer array.   
int* arr = new int[3]; // dynamic integer array.

答案 4 :(得分:8)

明确定义术语的含义非常重要。遗憾的是,静态和动态数组的含义似乎存在多种定义。

Static variables是使用static memory allocation定义的变量。这是一个独立于C / C ++的通用概念。在C / C ++中,我们可以创建具有全局,文件或本地范围的静态变量,如下所示:

int x[10]; //static array with global scope
static int y[10]; //static array with file scope
foo() {
    static int z[10]; //static array with local scope

Automatic variables 通常使用stack-based memory allocation实施。可以在C / C ++中创建一个自动数组,如下所示:

foo() {
    int w[10]; //automatic array

这些数组x, y, zw的共同点是每个数组的大小是固定的,并在编译时定义。

理解自动数组和静态数组之间区别很重要的原因之一是静态存储通常在目标文件的data section(或BSS section)中实现,并且编译器可以使用绝对地址访问数组,这对于基于堆栈的存储是不可能的。

dynamic array通常意味着什么不是可调整大小的,而是使用dynamic memory allocation实现的,具有在运行时确定的固定大小。在C ++中,这是使用new operator完成的。

foo() {
   int *d = new int[n]; //dynamically allocated array with size n     

但是可以使用alloca创建一个在运行时定义的修复大小的自动数组:

foo() {
    int *s = (int*)alloca(n*sizeof(int))

对于真正的动态数组,应该使用C ++中的std::vector(或variable length array in C)。

OP问题中的作业意味着什么?我认为很明显,所需要的不是静态或自动阵列,而是使用new运算符使用动态内存分配或使用例如非固定大小的数组。 std::vector

答案 5 :(得分:3)

我认为在这种情况下,它意味着它在大小固定的意义上是静态的。 使用std :: vector。它有一个resize()函数。

答案 6 :(得分:1)

您可以拥有一个伪动态数组,其中大小由用户在运行时设置,但之后会被修复。

int size;
cin >> size;
int dynamicArray[size];

答案 7 :(得分:1)

静态数组

  1. 在编译时为静态数组分配了内存。
  2. 大小是固定的。
  3. 位于堆栈存储空间中。
  4. 例如:int数组[10]; //大小为10的数组

动态数组:

  1. 在运行时分配内存。
  2. 大小不固定。
  3. 位于堆内存空间中。
  4. 例如:int * array = new int [10];

答案 8 :(得分:0)

是的,在编译时创建静态数组,在运行时创建动态数组。到目前为止,差异与其内存位置有关,静态位于堆栈上,动态在堆上创建。位于堆上的所有内容都需要内存管理,除非存在垃圾收集器(如.net框架的情况),否则存在内存泄漏的风险。

答案 9 :(得分:0)

静态数组:效率。不需要动态分配或解除分配。

在C,C ++中声明的包含静态修饰符的函数是静态的。 示例:static int foo [5];

答案 10 :(得分:-3)

静态数组meens,在数组的侧面给出元素

动态数组意味着不给出数组侧面的元素

示例:

     char a[10]; //static array
       char a[];  //dynamic array