使用运算符new/malloc分配的内存块是否可以在程序执行结束后持续存在?

bad*_*ash 14 c c++ dynamic-memory-allocation

可能重复:
退出C应用程序时,是否自动释放了malloc-ed内存?

当我读到关于在C/C++中动态内存分配时分别使用delete/free是多么强制时,我才想到这个问题.我想如果内存分配持续超出我的程序执行终止,那么是的,它是强制性的; 否则,为什么我要担心释放分配的空间?操作系统是否会在进程终止时自动释放它?我是对的吗?我的问题是可以的

int *ip = new int(8);
Run Code Online (Sandbox Code Playgroud)

坚持超越我的计划终止?

Lin*_*ios 15

简答:不.

答案很长:没有.除非你做的工作要做,否则C++永远不会留下记忆.释放内存的原因是:

如果你没有释放内存,但继续分配它,你会在某个时候耗尽.一旦你用完了,几乎任何事情都可能发生.在Linux上,可能会激活OOM杀手并且您的进程被终止.也许操作系统会将您完全归档到磁盘.如果你使用足够的内存,也许你给Windows框一个蓝屏.它几乎可以被认为是未定义的行为.此外,如果你泄漏内存,它只是在那里选址,未使用,未发布,没有人可以使用它,直到你的进程终止.

还有另一个原因.当您向分配器释放内存时,分配器可能会将其保留,但只需将其标记为可用.这意味着下次你需要记忆时,它已经坐在那里等着你.这意味着内核调用内存的次数越少,性能就越高,因为上下文切换效率非常低.

编辑:C和C++标准甚至不保证终止后操作系统将清理内存.许多操作系统和编译器可能,但不能保证.尽管如此,所有主要的桌面和移动操作系统(除了可能是DOS和一些非常旧的嵌入式系统)都会在它之后清理进程内存.

  • 它没有被"修复",因为当父进程使用大量内存时,它显然会破坏`fork()`/`exec()`的组合:http://www.quora.com/What-are -the-缺点 - 的 - 禁用 - 内存过量使用功能于Linux的 (4认同)
  • 这个答案非常以Linux为中心。我完全不确定*语言*能保证这种行为。 (2认同)
  • @Damon:你为什么要叫OOM杀死憎恶?当一个系统*真正*内存不足(没有更多物理,没有更多交换),那么系统必须做*某事*,不是吗?为什么杀死犯罪过程是一件坏事?只要它可以配置,以便您的任务关键型服务器进程不是那样的. (2认同)

das*_*ght 6

在程序退出之前,您无需将内存释放回操作系统,因为操作系统将回收在进程终止时分配给进程的所有内存.如果在完成流程之前分配了所需的对象,则不必释放它.

尽管如此,仍然最好释放内存:如果你的程序经常使用动态内存,你几乎肯定需要运行内存分析器来检查内存泄漏.探查器将告诉您最后没有释放的块,您需要记住忽略它们.将泄漏次数保持为零会好得多,原因同样是可以消除100%的编译器警告.


lio*_*ori 6

历史记录:旧 Amiga 计算机 (\xe2\x80\x9cAmigaOS\xe2\x80\x9d) 使用的操作系统没有像现在假设的那样具有完整的内存管理功能(除了 Amiga 不存在时发布的某些更高版本)更受欢迎)。

\n\n

CPU 没有 MMU(内存管理单元),因此每个进程都可以访问所有物理内存。因此,当两个进程想要共享一些信息时,它们只需交换指针即可。这种做法甚至受到操作系统的鼓励,操作系统在其消息传递方案中使用了这种技术。

\n\n

然而,这使得无法跟踪哪个进程拥有哪一部分内存。因此,操作系统没有释放已完成进程的内存(或任何其他资源,事实上)。因此,释放所有分配的内存至关重要。

\n


San*_*nto 5

1)当您请求脱离堆时释放内存。内存泄漏从来都不是一件好事。如果它现在没有伤害你,它很可能会在以后发生。

2) C 或 C++ 不保证您的操作系统会为您清理内存。有一天,您可能会在一个系统上进行编程,但实际上并没有。或者更糟糕的是,您可能会将不关心内存泄漏的代码移植到这个新平台。

  • 任何不清理这些内存的操作系统都是垃圾。这意味着该操作系统上的任何应用程序崩溃都将永远留下这些泄漏的资源。标准 malloc/new 创建应用程序内存,没有理由相信它会在该应用程序结束后持续存在。 (3认同)