刚开始学习C语言时遇到了以下问题:
我需要在C语言中缩小整数数组,删除末尾的元素。通过删除,我的意思是释放内存。常见的答案是为较小的数组分配新内存,之后将原始数组的所有项(-要删除的项)复制到新分配的内存中,然后使用free()释放原始数组。
由于我必须处理非常大的数组,我宁愿跳过复制部分。
是否可以创建一个指向“原始数组接近末尾”的指针变量,其大小为“数组末尾-接近末尾”,然后释放该指针?
提前感谢
来自C标准库的realloc函数可能是您想要的。
在您的情况下,由于内存管理器没有理由分配新的内存区域,因此很可能不会执行任何复制操作。系统只能将旧大小和新大小之间的差异作为可用内存回收。
如果您使数组变得更大,则会发生复制,因为malloc等函数不能保证“当前”区域后面的内存实际上是空闲的。如果是这样,当前内存分配将扩展。 否则,需要找到一个更大的可用内存区域,并且可以在内存中的任何位置进行分配。
realloc
?它是与内存分配相关的函数。int main(void)
{
int *array = NULL, *tmp;
if(!(array = malloc(5 * sizeof(int)))) return 1;
if(!(tmp = realloc(array, 2*sizeof(int))))
{
free(array);
return 1;
}
array = tmp;
}
你可以不使用tmp
指针,仅使用 array = realloc(array, 2 * sizeof(int)))
,但这可能会在以后出现问题。
可以设计一个内存管理器来实现这一点,但是常用的内存管理器都没有这个属性。您可以编写自己的内存管理器并将其用于这些数组。
我会使用realloc。Realloc可能会复制内存,但这仍然比自己编写内存管理来解决复制问题更高效。
有人会告诉你,当结果大小较小时,没有良好行为的C库不会复制。他们可能是对的。然而,我不使用或编写商业C库,所以就我而言,这个说法没有证据支持。
realloc
来缩小内存。虽然不是所有的实现都能保证,但有些实现会直接返回你传入的原始指针,而不进行任何复制。 - cnicutarrealloc
吗? - Keith Millerfree()
函数不可能通过传递一个指针“接近末尾”来释放内存块的一部分。那几乎肯定会导致崩溃或堆损坏。 - Blastfurnace