malloc还是普通的数组定义?
什么时候我应该在C中使用malloc而不是普通的数组定义?
我无法理解之间的区别:
int a[3]={1,2,3} int array[sizeof(a)/sizeof(int)]
和:
array=(int *)malloc(sizeof(int)*sizeof(a));
通常,在以下情况下使用malloc()
:
- 数组太大而无法放在堆栈上
- 数组的生命周期必须比创建它的范围更长
否则,使用堆栈分配的数组。
int a[3]={1,2,3} int array[sizeof(a)/sizeof(int)]
如果用作局部变量,则将在堆栈上分配a
和array
。 堆栈分配有其优点和缺点:
- 亲:它非常快 – 它只需要一次寄存器减法操作来创建堆栈空间和一次寄存器加法操作来回收它
- con:堆栈大小通常是有限的(并且在Windows上的链接时也是固定的)
在这两种情况下,每个数组中的元素数量是一个编译时常量: 3
显然是一个常量,而sizeof(a)/sizeof(int)
可以在编译时计算,因为a
的大小和int
的大小都是在声明array
时已知。
如果仅在运行时知道元素的数量,或者当数组的大小太大而无法安全地适应堆栈空间时,则使用堆分配:
array=(int *)malloc(sizeof(int)*sizeof(a));
正如已经指出的那样,这应该是malloc(sizeof(a))
因为a的大小已经是它所占用的字节数而不是元素的数量,因此不需要额外乘以sizeof(int)
。
堆分配和释放是相对昂贵的操作(与堆栈分配相比),并且应该根据它提供的好处仔细加权,例如在紧密循环中被多次调用的代码中。
现代C编译器支持C标准的C99版本,它引入了所谓的可变长度数组(或VLA),类似于其他语言中可用的类似function。 VLA的大小在运行时指定,就像在这种情况下:
void func(int n) { int array[n]; ... }
仍然在堆栈上分配array
就好像通过调用alloca(3)
分配了数组的内存一样。
如果你不希望你的数组有一个固定的大小,你绝对必须使用malloc() 。 根据您要执行的操作,您可能事先不知道给定任务需要多少内存,或者您可能需要在运行时动态调整数组大小,例如,如果有更多数据,您可能会放大它进来。后者可以使用realloc()完成而不会丢失数据。
不要像在原始post中那样初始化数组,而应该只是初始化指向整数的指针。
int* array; // this variable will just contain the addresse of an integer sized block in memory int length = 5; // how long do you want your array to be; array = malloc(sizeof(int) * length); // this allocates the memory needed for your array and sets the pointer created above to first block of that region; int newLength = 10; array = realloc(array, sizeof(int) * newLength); // increase the size of the array while leaving its contents intact;
你的代码很奇怪。
标题中问题的答案可能类似于“当你需要很少量的短暂数据时,使用自动分配的数组,使用malloc()
进行堆积分配”。 但是很难确定答案,这在很大程度上取决于具体情况。
不知道为什么你首先显示一个数组,然后另一个数组试图从第一个数组计算它的长度,最后一个malloc()
调用尝试做同样的事情。
通常,您可以了解所需元素的数量,而不是要模拟其大小的现有数组。
第二行更好:
int array[sizeof a / sizeof *a];
不需要重复依赖a的类型,上面将array
定义为int
数组,其元素数量与数组a
。 请注意,这仅在a
确实是数组时才有效。
此外,第三行应该是:
array = malloc(sizeof a);
关于sizeof
参数,不需要太聪明(特别是因为你弄错了),并且不需要malloc()
的返回值 。