如何在C++中重新分配内存,即使realloc()失败了

3

malloc()成功分配内存后,有时程序需要增加数组的大小。虽然malloc()已经成功工作,但realloc()失败了。

我使用了以下代码来处理realloc()的失败情况。 这里的T是模板参数。array是类型为T的指针,_size是已经使用的数组总索引,_maxSize是可用索引的最大数量。 当_size达到_maxSize时,需要重新分配内存。

if(_size == _maxSize){
    _maxSize *= 2;
    T *temp;
    temp = (T *) realloc( array, sizeof( T ) * (_maxSize) ) ;
    if(temp == NULL){
        printf("...reallocation of memory failed...\n");
        exit(0);
    }
    else{
        array = temp;
    }
}

虽然realloc()的失败已经处理了,但程序确实需要增加数组大小,即使realloc()失败,我也不知道如何执行重新分配。


这段代码是用C++编写的@BasileStarynkevitch - Parvez Mia
在我看来,如果 realloc() 失败,任务几乎失败了。该应用程序可能需要大量内存或可用内存非常有限。(这是嵌入式系统吗?)您必须查找应用程序中的内存泄漏或确实需要更多内存。在后一种情况下,我会考虑将数据(从文件中读取?)拆分为部分进行处理。 - Scheff's Cat
2
你认为分配器是出于恶意而拒绝分配内存的吗?还有一个隐藏的内存储藏处,可以通过其他手段而不是realloc来访问它吗? - molbdnilo
2
这里的T是模板参数。这段代码是C++语言,尽管它使用了一种非常类似于C语言的内存分配方式。 - Remy Lebeau
1
注意(与问题无关):如果这是 C++,并且 T 是一个模板类型,那么你必须非常小心地在正确的时间手动调用其放置构造函数/析构函数 - 你没有提供所有代码,所以我们不能验证你是否这样做。事实上,使用 realloc 甚至不会给你机会去做对 - 它有时会移动内存,而你没有机会调用析构函数。你简单地不想以这种方式做 - 它只能在有限数量的情况下工作,并且太危险了。 - Mike Vine
显示剩余3条评论
1个回答

6

如何在C++中重新分配内存,即使realloc()失败

在真正的C++中,你永远不会使用mallocrealloc,只需使用new(它实现于你的C++标准库实现中,并将在内部调用malloc!)和delete(它通常调用free),最好使用标准容器智能指针。内存不足的情况由异常处理(例如std::bad_alloc),你可以catch这些异常。

在C语言中,健壮的解决方案是不使用realloc而是使用malloc、calloc和free(通过memset来清除区域,通过memcpy来复制区域)。 真正的问题是如何巧妙地处理内存不足的情况。这是一个设计问题,与应用程序相关。了解记忆化和垃圾回收技术、概念和术语。注意到引用计数是一种基本的C++垃圾回收技术。因此阅读GC手册或至少追踪垃圾回收维基页面以学习它将教给您的概念。

请注意内存过度提交。这是我不喜欢的操作系统功能。

还要注意,mallocfree(在您的C标准库实现中实现)使用操作系统原语(通常是系统调用)。因此,请阅读更多关于操作系统的信息,例如{{link4:操作系统:三个简单的部分}}。在Linux上,这些操作系统原语通常是mmap(2)munmap(2)。由于系统调用成本高昂,您的标准库将尝试避免它们,并优先标记free的内存区域以便未来malloc使用。

使用valgrind来查找内存泄漏。你更喜欢在一些Linux发行版上开发C++代码,只是为了拥有valgrind。我的意见是Linux提供了一个非常友好的开发环境,所以我推荐大多数程序员和学生使用Linux。不要忘记使用g++ -Wall -g进行编译(也许在基准测试时还要使用-O2),并在需要时使用地址泄漏检测器

更普遍地说,请阅读http://norvig.com/21-days.html-它提供了很好的见解。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接