constexpr 数组与双端队列,内存利用率
Posted
技术标签:
【中文标题】constexpr 数组与双端队列,内存利用率【英文标题】:constexpr array vs deque, memory utilization 【发布时间】:2021-12-28 05:31:53 【问题描述】:我需要在我的代码中存储大约 30 个整数的预先已知大小,我已经准备好了
constexpr std::array<size_t, 30> MAPPING1, 2, 3, ...;
如果我没记错的话,上面会在编译时进行评估,但它也会占用一个大小为 30 个整数的单个顺序内存块?
如果是这样,是否值得使用 std::deque 代替
const std::deque<int> MAPPING1, 2, 3, ...;
这样,对于双端队列,我们不会使用单个大的顺序内存块,而是使用一堆碎片块,因此即使内存碎片也能正常工作?
如果我遗漏了什么,请告诉我,谢谢
【问题讨论】:
数组总是一个连续的内存块。它是固定大小的(即它的大小在编译时已知)双端队列是一个动态容器,它可以在运行时增大大小。 Deque 对其内容使用动态分配(每个项目都分配在不同的位置),而如果您不自己在动态存储上分配它,则数组不会。 如果您已经知道大小,为什么还要考虑出队? IMO 碎片对于如此小的分配是不值得担心的。使用array
。此外,deque
将使用更多内存,因为它需要记账。
【参考方案1】:
这里不值得使用std::deque
。
它还会占用一个大小为 30 个整数的连续内存块吗?
是的,它会占用一个大小为 30 个整数的连续内存块在堆栈中
这样,对于双端队列,我们不会使用单个大的顺序内存块,它可能会使用一堆碎片块,因此即使内存是碎片的,它也能正常工作?
它是implementation-dependent,对于 30 个整数,它们可能会被分成几个小块,也可能不会,但它会使用 堆 内存,因此会产生运行时开销:
与 std::vector 不同,双端队列的元素不被存储 连续的:典型的实现使用一个单独的序列 分配的固定大小的数组,带有额外的簿记,这意味着 对双端队列的索引访问必须执行两个指针解引用, 与向量的索引访问相比,它只执行一次。
根据@Homer512的评论,我们在使用堆的时候还需要注意内存碎片,可能存在内存浪费,我们无法避免。
【讨论】:
好答案。我没有检查过 VC,但 gcc 使用 512 字节的固定块作为其双端队列。或 128 个整数。也许值得注意。我还要补充一点,现在堆碎片问题比历史上要少得多。尤其是在 64 位中,这不值得担心 @Homer512 感谢您提供如此出色的补充!我想参考您的评论。 感谢您的回答和澄清,我现在明白了:-)以上是关于constexpr 数组与双端队列,内存利用率的主要内容,如果未能解决你的问题,请参考以下文章