巨大的内存分配:堆栈与堆
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了巨大的内存分配:堆栈与堆相关的知识,希望对你有一定的参考价值。
我做了一个需要1 GB内存的结构。当我在堆上分配它时,程序启动很快,我在应用程序管理器中看到,它的内存使用达到了这个数量,但当我在堆栈上分配它就像一个简单的变量时,应用程序需要更多的时间来启动在应用程序管理器中,我看到它没有使用那么多的内存(只有几KB)。为什么?这是否意味着建议在堆中存储大量数据?那个案子更快吗?我知道通常在堆栈上分配内存因为映射等而更快,但在这种情况下,它很奇怪。谁能解释一下这个?提前致谢!
在典型的桌面系统上,默认情况下堆栈的大小通常在1到几兆字节左右。嵌入式设备可能更少。
如果分配的内存多于堆栈上的内存,操作系统通常会在您尝试访问内存时立即终止程序。
这是否意味着建议在堆中记录大量数据?
建议对大量数据使用免费存储(动态分配),因为大量数据会溢出堆栈。
应用程序管理器我看到它没有使用那么多的内存(只有几KB)。
通常,操作系统在访问该内存时为进程分配一页内存。由于您的程序没有因堆栈溢出而崩溃,我怀疑您从未访问过内存,因此没有为数据分配内存。
是的,建议动态地进行大量分配 - 因为那时你可以优雅地应对失败(obligatory note on terminology)。
例如,这个:
void might_throw(size_t sz) {
std::vector<int> v(sz);
// ...
}
如果它因为足够大的std::bad_alloc
而失败,则会抛出sz
,这意味着我可以选择捕获异常并使用较小的数字重试。即使我无法有效恢复,堆栈展开也可以安全地清理我的其他对象。
反过来
void will_just_die() {
int a[SomeEnormousConstant];
// ...
}
如果无法真正创建a
,则没有恢复机制。程序将崩溃,很难,没有堆栈展开或(标准)错误处理机制。
这可能会立即发生,或者只有当您实际尝试访问更多的a
而不是成功分配时才会发生。如果你非常不走运,它甚至可能会起作用,但会破坏别的东西。
外部显示给定分配的详细信息非常依赖于操作系统,我不确定您使用的是什么 - 应用程序管理器是OSX吗?
大型动态分配直接映射是很常见的,在这种情况下,它会立即显示为虚拟大小的增加,但除了访问之外,可能仍然不会分配任何物理页面。
如果自动(“堆栈”)分配只是执行帧指针算术并再次依赖于物理页面的延迟分配,则这不会影响虚拟或物理大小(再次,直到您尝试实际访问该内存)。
我不知道为什么启动自动版需要更长的时间 - 你必须提供一个MCVE,这实际上是可重现的,以及你的操作系统/平台细节,以获得答案。
以上是关于巨大的内存分配:堆栈与堆的主要内容,如果未能解决你的问题,请参考以下文章