malloc() 和 realloc() 结构
Posted
技术标签:
【中文标题】malloc() 和 realloc() 结构【英文标题】:malloc() and realloc() of structures 【发布时间】:2021-01-15 08:25:23 【问题描述】:我们可以为结构动态分配内存吗?这是处理动态分配结构的正确程序吗?请告诉我如何malloc()
和realloc()
一个结构。
newnode 是 struct List * 类型,但是在开始索引时它会转换为 struct List。这种转换如何可能?我的插入函数只接受 (struct List*) 我在某处错了吗?
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct List
char val[20];
;
void insert(struct List *);
int main(void)
int i = 0;
int size = 1;
struct List *newnode = (struct List *)malloc(size * sizeof(struct List));
for (i = 0; i < 5; i++)
if (size <= i)
size = size + size;
newnode = (struct List *)realloc(newnode, size * sizeof(struct List));
scanf("%s", newnode[i].val);
insert(newnode[i]);
for (i = 0; i < 5; i++)
printf("%s\n", newnode[i].val);
return 0;
void insert(struct List *node)
printf("%s\n", node->val);
【问题讨论】:
它可以编译吗? -> 它没有。realloc
的处理是错误的,如果 realloc
失败,你也会丢失原始数组......
为什么relloc
错了 什么是正确的实现方式?
见这里:***.com/q/38213123/10871073 和这里:***.com/q/605845/10871073
"这是一个正确的过程吗" --> 最后缺少free()
。
感谢您的快速回复......还有一个问题,newnode 的类型是 struct List * 但是当开始索引时它会转换为 struct List。这种转换如何可能?我的插入函数只接受(struct列表*) 我是不是哪里错了?
【参考方案1】:
是的,这很好,只是您将返回值分配给原始数组指针。 realloc()
如果无法调整内存大小,则返回 NULL
。您需要将其分配给一个临时变量,如果值为NULL
,请不要覆盖a
。
您需要注意的主要事情是指针,而您的struct
没有。在这些情况下,指向的内存不是分配数组的一部分。
【讨论】:
【参考方案2】:除了 3 个问题之外,代码可以正常工作:
您不测试内存分配失败。如果无法分配内存,malloc()
和 realloc()
都将返回 NULL
:如果发生这种情况,在取消引用 newnode
时会出现未定义的行为。
要优雅地处理realloc()
失败的情况,您应该将重新分配的指针存储到不同的变量,以便您仍然可以访问尚未释放的前一个数组并释放它。
scanf("%s", newnode[i].val);
是一个安全漏洞:您应该限制可以存储到目标数组的字节数
scanf("%19s", newnode[i].val);
您没有测试scanf()
的返回值来检测无效或丢失的输入。
insert()
没有插入任何东西。
这里是一个修改后的版本,带有错误处理和较少混淆的名称:
#include <stdio.h>
#include <stdlib.h>
struct Item
char val[20];
;
//void insert(struct Item *);
int main(void)
int i, j;
int size = 0;
struct Item *array = NULL;
for (i = 0; i < 5; i++)
if (i >= size)
int newsize = size ? 1 : size + size;
struct Item *newarray = realloc(array, sizeof(*array) * size);
if (newarray == NULL)
perror("cannot reallocate the array");
break;
size = newsize;
array = newarray;
if (scanf("%19s", array[i].val) != 1)
fprintf(stderr, "missing input\n");
break;
//insert(array[i]);
for (j = 0; j < i; i++)
printf("%s\n", array[i].val);
free(array);
return 0;
【讨论】:
IDK,也许是为了开始这样有趣的对话? (社会工程机器人);-) IAC,我会使用struct List *newnode = realloc(node, sizeof *node * size);
甚至void *newnode = realloc(node, sizeof *node * size);
。很多方式都可以接受。
@chux-ReinstateMonica:很好的建议,但为了避免一元和二元*
的组合有些混乱,我更喜欢使用多余的括号并写成void *newnode = realloc(node, sizeof(*node) * size);
它不是列表,只是结构数组。
@P__J__:我同意struct
标签和变量名的选择相当混乱。以上是关于malloc() 和 realloc() 结构的主要内容,如果未能解决你的问题,请参考以下文章
alloc()malloc()calloc()realloc()区别及用法
C:malloc/calloc/realloc/alloca内存分配函数
堆的分配和释放(malloc,free,calloc,realloc)