2010-12-12 42 views
0

我想现在这些指令是如何分配内存的。C++ new/new [],它如何分配内存?

例如如果我得到了代码:

x = new int[5]; 
y = new int[5]; 

如果这些被分配它是如何看起来像RAM? 是否为每个变量或块(内存页或您如何调用它 - 32位上的4KB大小)为2个变量共享保留了整个块?

我在任何手册中都找不到我的问题的答案。感谢所有回复。

我在维基百科上找到: 页面的内部碎片 很少进程需要使用精确数量的页面。结果,最后一页可能只会部分满,浪费了一些内存。较大的页面大小通过这种方式显然增加了浪费内存的可能性,因为更多可能未使用的内存部分被加载到主内存中。较小的页面大小确保与分配中所需的实际内存量更加匹配。例如,假设页面大小为1024KB。如果一个进程分配1025KB,则必须使用两个页面,导致1023KB未使用空间(其中一个页面完全占用1024KB,另一个页面仅占用1KB)。

这就是我的问题的答案。无论如何,谢谢你们。

回答

4

一个典型的分配器实现将首先调用操作系统来获取巨大的内存块,然后满足您的请求它会给你一块内存,这就是所谓的子分配。如果内存不足,它将从操作系统中获得更多。

分配器必须跟踪它从操作系统获得的所有大块,以及它发给客户的所有小块。它也必须接受来自客户的阻止。

典型的子分配算法保持称为空闲列表每个尺寸的返回块的列表和总是试图满足来自空闲列表的请求时,仅将主块如果空闲列表是空的。这种特殊的实现技术对于普通程序来说非常快速而且非常高效,尽管如果请求大小遍布整个地方(这在大多数程序中并不常见),它就会出现可怕的碎片属性。

像GNU的malloc实现这样的现代分配器很复杂,但是已经有数十年的经验,并且应该被认为是非常好的,以至于很少需要编写自己的专用suballocator。

+0

所以一个小问题:现在在我的系统(debianx64)上,页面大小是4096字节。有没有可能减少它?我想在内存中存储很多小块,但即使保留1个字节,我也不能使用另一个4095,因为此处添加了第1条消息中的内容。这是真的还是我错了? – 2010-12-12 13:42:34

4

您没有在手册中找到它,因为它没有被标准规定。也就是说,大部分时间x和y将并排(继续并且他们的地址是cout<< hex <<)。

但是标准中没有任何东西强制这个,所以你不能依赖它。

1

每个进程有相关联的不同片段,其沿所述进程的地址空间中划分: 1)文本段::当您的代码放置 2)堆栈段::进程堆栈 3)数据段::这是其中“新”的内存被保留。除此之外,它还存储初始化和未初始化的静态数据(bss等)。因此,无论何时你调用一个新的函数(我猜想在内部使用malloc,但新类使得它更安全地处理内存),它会在数据段中分配指定数量的字节。 当然,您在运行程序时打印的地址是虚拟的,需要转换为物理地址..但这并不是我们的头痛,OS内存管理单元对我们来说也是如此。