静态数据类型是一种在内存中具有固定大小的数据类型。当我们提前声明数组大小时,会在内存中保留很多字节或空间,以后无法再增加。因此,数组是静态数据类型。
好。但是我们可以使用指针或指针数组为数组动态分配内存。我不清楚整个概念。请帮助
答案 0 :(得分:6)
概念是:
// example 1
int array1[256]; // a fixed size, global array of 256 ints, statically allocated
void example2(void)
{
int array2[256]; // an array of fixed size 256, allocated when the function is entered
//...
//... // and automatically released (deallocated) when the function exits
}
void example3(int n)
{
int array3[n]; // an array of fixed size n, allocated when the function is entered
//...
//... // and automatically released (deallocated) when the function exits
}
void example4(int n)
{
int *array4;
array4= malloc(n*sizeof(int)); // a dynamically allocated array
//...
free(array4); // that must be manually deallocated when no longer needed
}
在第一个示例中,数组的大小在编译时确定,并在程序执行期间固定。在整个程序执行期间,该数组驻留在全局内存中。
在第二个示例中,数组的大小也在编译时确定,并且在程序执行期间保持固定,但是在输入函数时在堆栈上分配了内存。因此,在递归函数中,此数组可以同时存在多个。
第三个示例使用了更高版本的C标准(VLA)的可变大小数组。数组大小在函数执行期间是固定的,但可以在每次函数调用时更改。如果n
大,则很容易耗尽堆栈空间,从而导致程序崩溃。
第四个示例使用指针从堆中动态分配数组。通过重新分配数组,在调用函数期间其大小也可以更改。堆通常比堆栈大得多,因此对于大型数组,首选此方法。由于该数组不位于堆栈上,因此您可以将其返回给调用方(调用方在不再需要该调用方时必须小心以释放它)。
答案 1 :(得分:1)
根据我的理解,您在理解数组和动态内存之间的差异时遇到了一些困难。
无论何时声明数组,例如:
char array[10];
您要在堆栈中分配10个chars
(因此大部分时间为10个字节)。
但是程序不仅具有分配数据的堆栈,还具有堆。由于数组的大小在编译时是已知的,因此可以分配它。但是,如果在编译时不知道内存量并且需要动态分配内存,该怎么办?然后,您可以在堆中分配所需的内存,并将指针放在堆栈中。例如:
char *ptr;
在堆栈中分配指针,然后可以使用malloc(或calloc)在堆中分配所需的内存:
ptr = malloc(10 * sizeof (char));
这将在堆中分配10个字节的内存。
一方面,释放堆栈时,数组会自动释放;另一方面,必须显式释放堆中分配的内存,否则可能会发生内存泄漏。
另一个要注意的是,当运行多个线程时,每个线程都有自己的堆栈,但是它们都共享相同的堆。在运行多个进程时,每个进程都有自己的堆栈和堆。