c++ - "Memory Fragmentation"这还是个问题吗?

标签 c++ memory-management memory-fragmentation

<分区>

我有点困惑。在操作系统类(class)中,我们被告知所有操作系统都通过分页或分段处理内存碎片,并且根本没有连续的物理内存分配。操作系统使用不同级别的寻址(逻辑/物理)来避免连续的内存分配。现在here有很多关于它的讨论。我的问题是: 这个问题在支持逻辑寻址的操作系统的 C++ 编程中是否真实存在(是否有任何进程仅因为内存碎片而崩溃)?如果是,为什么首先每个操作系统都试图避免连续寻址?

最佳答案

有两层:虚拟进程地址空间中的碎片和物理内存中的碎片。

如果您查看任何现代应用程序,您会发现它的内存使用量是如何随着时间的推移而增长的,因为内存没有释放给操作系统。您可以说这是由其他原因引起的,但内存碎片(例如,分配的内存块的位置不连续)是造成这种情况的核心原因。简而言之,内存分配器拒绝向操作系统释放内存。

如果您对物理内存中的碎片感兴趣,那么即使内存按页组织,仍然需要分配物理上连续的内存块。例如,如果您需要避免虚拟内存开销,您可能希望使用大页面(Linux 中的“大页面”)。 x86_64 支持 4KiB、2MiB 和 1GiB 页面。如果没有所需大小的连续物理内存,您将无法使用它们。

如果操作系统是指“内核”,那么它无法帮助您处理进程地址空间中发生的碎片(堆碎片)。 C 库应该尽量避免碎片化,不幸的是,它并不总是能够这样做。查看链接 question .

内存分配器通常无法释放大块内存,如果其中至少有一些分配的话。有一个部分解决方案利用页面中的虚拟内存组织 - 所谓的“无惰性”机制,由 MADV_FREE 表示在 Linux 和 BSD 上以及 DiscardVirtualMemory在 Windows 上。当你有一大块内存只被部分使用时,你可以通知内核那部分内存不再需要了,它可以在内存压力下收回它。这是延迟完成的,并且仅在内存压力下完成,因为内存释放非常昂贵。但是出于性能原因,许多内存分配器仍然不使用它。

所以您问题的答案 - 这取决于您对程序效率的关注程度。大多数程序并不关心,因为标准分配器只是为它们完成工作。当标准分配器无法有效地完成其工作时,某些程序可能会受到影响。

关于c++ - "Memory Fragmentation"这还是个问题吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52018123/

相关文章:

c++ - 基本 GL 函数 glTranslatef 似乎不起作用

c - 在 realloc() 之前需要 malloc() 吗?

c++ - 哪种内存分配算法最适合性能和时间要求严格的 C++ 应用程序?

c++ - 如何在 C/C++ 中声明 16 位二进制字符?

c++ - 将 wstring 转换为 TCHAR 的问题

c++ - 如何知道模板类中另一个模板类的类型

ios - 数组中的 Swift 闭包在 Objective-c 中变为 nil

iOS 内存分配——一个应用程序可以使用多少内存?

c - 如何获得可以分配的最大可用内存块?