4

在 C++ 中使用 new 或 malloc 进行动态分配是否有任何类型的限制、系统或其他限制?系统是 64 位的,我想分配一个大约 8 亿个结构的数组。

编辑:我之前没有自己测试它的原因是因为我目前无法访问具有足够内存的机器,所以我觉得在我当前的机器上测试它没有意义。

在运行我自己的测试之后,我可以很好地分配 8 亿个元素,但是一旦我达到 ~8.5 亿,malloc 就会返回 NULL。该结构包含 7 个浮点数,因此总大小约为 22GB。这个看似任意的限制背后的原因是什么?这台机器有 4GB 的内存和 4GB 的虚拟内存,所以我不知道为什么我什至能够分配这么多。

4

3 回答 3

3

除了尝试运行代码之外,没有其他方法可以告诉您。

“位数”仅表示您所针对的操作系统和体系结构,我还想强调一个事实,即每个支持 C++ 程序的操作系统都有自己的标准 C++ 库的实现(如果您使用的是 std 库)并且作为编码器,您只是使用属于 std 库的标头和命名空间,并且您依赖于操作系统通常随附的 C/C++ 库来实际运行您的代码。

我还建议依靠测试部分,将内存的使用保持在最低限度,有些操作系统也有一些防溢出技术或类似的东西,所以有些操作系统会把你的大量分配视为对系统稳定性的威胁,大量使用 RAM 还涉及到内存控制器的重要作用,就像 X86 架构中的正常情况一样,通常您尝试做的不是一件好事,结果很糟糕,或者最终以真正特定的机器和操作系统作为您的您尝试创建的此应用程序最喜欢的目标。

最后,您正在尝试编写 C 代码而不是 C++ 代码!

malloc()是来自 C 世界的一个函数,还涉及直接内存管理,如直接分配和取消分配,你的硬件也必须执行很多,我的意思是,很多间接的大约 8 亿个结构。

我建议切换到一个真正的 C++ 结构,比如 std 向量(比性能列表更好),或者只是切换到一种具有自己的垃圾收集器并且没有像 C# 或 Java 这样的直接内存管理阶段的语言。

您的问题的答案是否定的,同样从务实的角度来看,您将面临优化代码的一个大问题,而且我可能会说,使用 C++ 或 C# 或 Java 等不同的语言,您的生活会更轻松,但是请记住,垃圾收集器通常需要大量内存,在您的情况下,最好的解决方案可能是 C++,您需要付出一些额外的努力和测试阶段。

于 2012-06-25T23:24:32.777 回答
3

限制大约是您的可用内存加上允许交换到磁盘的空间。创纪录的 8 亿字节 = 800 Mb,因此您可以在使用小型结构的情况下保持安全,甚至可能不需要交换(应该避免)只需尝试一下,看看它在哪里崩溃 ;-)

64 位:2^64/2^30 = 大约 17* 10⁹ 千兆字节(对于字节可寻址架构,1Gb=2^30 位)所以这里不用担心

32 位:2^32 = 大约 4 GB 所以即使在这里你也可以安全

有符号值除以二,至少在 64 位系统上你还有很多空间

于 2012-06-25T23:01:28.547 回答
0

对于动态分配,适用与静态分配相同的限制。例如,您只受可用内存量的限制(受指针大小的限制)。32 位和 64 位系统之间的主要区别在于指针的大小,在 32 位系统上,您只能使用 32 位指针,例如可以访问 4294967296 字节 (4GB)。系统保留了其中的一部分,因此最终大约为 2,5 GB。在 64 位系统上,2^64 = 16 exabyte,实际上大约是 256 TB 到 4 PB。远远超过你需要的。如果您没有足够的内存(也没有足够的交换空间),它可能会崩溃。

于 2012-06-25T23:19:44.893 回答