如果我的目的是创建一个动态大小的结构数组。有人可以向我解释一种分配内存以调整数组大小的方法如何按应有的方式工作;与将 x 个元素添加到数组后失败的元素相比?
以下方法使用malloc()
(不正确(。有人可以解释如何正确地为阵列分配内存吗?
struct some_struct{...data members...}*collection = NULL;
int total_elements;
int space_allocated; // the number of elements allocated to the array
void resize_array(){
if(total_elements == space_allocated) {
if(space_allocated == 0)
space_allocated =2;
else
space_allocated *= 2;
//where collection is a pointer to a struct
collection = malloc(space_allocated * sizeof(struct some_struct));
if(collection == NULL){
fprintf(stderr,"NO MEMORY ALLOCATED");
exit(EXIT_FAILURE);
}
}
}
与正确使用realloc()
为阵列动态分配内存的另一种方法相比。用于保存内存的 void* 类型变量的意义是什么?
void resize_array(){
if(total_elements == space_allocated){
if(space_allocated == 0)
space_allocated = 2;
else
space_allocated *= 2;
//why is a variable of type void allowed? What does that mean?
void* tmp = realloc(collection, ((num_allocated)*
sizeof(struct some_struct)));
if(!_tmp){
fprintf(stderr,"NO MEMORY ALLOCATED");
exit(EXIT_FAILURE);
}
//what is the significance of the pointer cast?
collection = (some_struct*) _tmp;
}
}
您应该使用malloc
分配第一次初始化,并使用realloc
调整其大小。
当您以第一种方式再次malloc
时(完全是废话(,系统会分配一个新的内存空间并返回地址。现在你做了一个很好的内存泄漏。
第二种方式看起来合乎逻辑,请记住,除了在某些编译器中,可以使用realloc
代替malloc
(其中重新分配内存NULL
(,但您可以使用malloc
进行第一次初始化并忽略它们的善意。
realloc
和malloc
都返回void*
,但最后它们都是 bytes(char
(。由于 C 很弱,因此您可能会也可能不会将返回类型强制转换为类型(指针(。但在 c++ 中,它是不同的。
您可以使用void *
类型,但我更喜欢使用正确的类型
struct some_struct *tmp = realloc(collection, num_allocated * sizeof *tmp);
临时变量用于避免错误路径中的内存泄漏:
if (!tmp) {
perror("realloc()");
free(collection);
goto err;
}
collection = tmp;
当collection
初始化为NULL
时,您始终可以使用realloc()
。 但您应该验证num_allocated * sizeof *tmp
不会溢出。