C ++分配的字节数多于要求的字节数?

时间:2015-09-27 19:13:40

标签: c++

int main(int argc, const char* argv[])
{
    for(unsigned int i = 0; i < 10000000; i++)
        char *c = new char;

    cin.get();
}

在上面的代码中,为什么我的程序会使用471MB内存而不是10MB内存?

2 个答案:

答案 0 :(得分:4)

RAM的分配来自运行时库和操作系统的共同努力。为了识别示例代码请求的一个字节,有一些结构可以向运行时标识这个内存。它有时是双链表,但它由操作系统和运行时实现定义。

您可以通过这种方式进行类比:如果您有一个链接列表容器,那么您感兴趣的只是您在每个链接中放置的内容,但容器必须指向其他链接容器以维护链表。

如果您使用调试器或其他调试工具来跟踪内存,这些结构可能会更大,从而使每次分配成本更高。

RAM通常不会从数组中分配,但可以重载新运算符以更改分配行为。它可能是从一个数组(在你的例子中是一个大的)中专门分配的,这样分配的行为就像你期望的那样,在某些应用程序中,这是控制内存和提高性能的特定策略(尽管细节通常更多)复杂而不是简单的插图)。

答案 1 :(得分:3)

分配不仅包含已分配的内存本身,而且至少有一个单词告诉delete它必须释放多少内存;此外,这是一个必须正确对齐的数字,因此在分配的char之后会有一定的填充,以确保下一个块正确对齐。在64位机器上,这意味着每个分配至少16个字节(8个字节用于保存大小,1个字节用于保存字符,7个字节用于确保正确对齐)。

然而,很可能不是唯一存储的数据;为了帮助内存分配器找到空闲内存,可能存储额外的数据;如果假设数据由三个指针组成,则每个分配一个总共40个字节,这与您的数据非常匹配。

另请注意,分配器还将从操作系统请求比实际分配所需的更多内存,因此不需要为每个小分配执行昂贵的OS调用。也就是说,运行时库从操作系统中分配更大的内存块,然后为程序的分配削减较小的内存块。因此,通常会有一些从操作系统分配的内存(因此显示在任务管理器中),但尚未分配给程序中的某个对象。