Skip to content

模型Model

动态数组

Dynamic array · Resizable array

以预留容量和偶发整体搬迁支持可变长度的连续序列结构。

形式陈述 ​

动态数组用一块连续的数组维护长度 n 与容量 C,始终满足 0≤n≤C。前 n 个槽位构成逻辑序列,其余槽位是预留空间。以下成本假定下标可装入机器字,访问、写入和复制一个元素各为常数时间,分配并初始化 C 个槽位至多花费 O(C)。

按下标读取为 O(1)。从空表开始,初始容量取固定正整数,例如 C=1。尾部追加在 n<C 时只写入一个槽位;在 n=C 时分配容量 C′=⌈γC⌉ 的新区块,其中固定常数 γ>1,复制现有元素后再追加。单次扩容需 Θ(n),但连续 m 次追加的总成本为 O(m),故追加的摊还成本为 O(1)。若允许零容量初态,第一次追加必须单独分配正容量,不能直接把零乘以增长因子。

以初始容量 1、容量翻倍为例,m≥2 时扩容复制的元素数恰为

1+2+4+⋯+2⌊log2⁡(m−1)⌋<2m.

m=0,1 时没有复制旧元素的工作。

加上每次追加自身的一次写入,总工作量仍为线性。若支持自动收缩,收缩阈值必须低于扩张阈值,例如装载率降到 1/4 时把容量减半;这样收缩后装载率回到 1/2,为下一次扩容留出足够间隔。

直觉

动态数组用空余空间购买增长余地。大多数追加只占用已经预留的下一个槽位,偶尔才整体搬家;昂贵搬迁不是消失了,而是由此前一长串便宜操作共同分摊。容量按常数因子增长的关键在于:每次搬迁后,新空位与已有元素同量级,所以在再次搬迁前必然发生足够多的新追加。

连续布局保留了普通数组的地址计算与缓存局部性,却也继承了它的限制。中间插入或删除会改变后缀元素的位置,通常仍需 Θ(n) 次搬移;“可变长”只解决容量管理,不会让所有位置的修改都变成常数时间。

容量翻倍与整体搬迁
例子与边界

从容量 1 开始依次追加元素,容量沿 1,2,4,8,… 增长。追加第五个元素时,容量从 4 扩为 8,这次操作复制四个旧元素后再写入新元素,明显不是最坏 O(1);但前四次追加已经跨过了足够多的便宜步骤,整段序列的总复制量受几何级数控制。对需要稳定低延迟的程序,这种摊还保证仍可能不够,因为某一次暂停会随数组大小增长。

若每次满时只把容量增加一格,第 k 次扩容要复制 k 个元素,前 m 次追加的复制总量为 1+2+⋯+(m−1)=Θ(m2),摊还常数界随即消失。收缩也会造成类似问题:若在装载率恰降到 1/2 时立刻缩半,那么一次删除触发收缩后,紧接着一次追加便可能再次扩张,交替操作会令结构在两个容量间反复整体复制。扩张与收缩阈值之间的滞回区正是为阻止这种抖动。

扩容还会使指向旧存储区的地址、迭代器或引用失效;哪些引用保持有效取决于语言和容器契约。容量是实现状态,不等于可观察的逻辑长度,也不能把尚未初始化的槽位当成序列成员。

推论与应用

动态数组是向量、可变列表、字节缓冲区与许多哈希表桶数组的常见底层表示。它把 O(1) 随机访问、良好局部性和摊还 O(1) 尾部追加组合在一起;若主要操作落在两个端点,循环数组实现的双端队列可避免首部操作搬移;若频繁修改中间位置,可以比较链表或分块结构,但还要计入定位位置的成本。

势能法可把空余容量或装载率偏离目标的程度编码成势,统一证明扩张与收缩的摊还界。工程实现还需考虑增长因子对空间与复制次数的取舍:因子较大减少搬迁,代价是更多闲置空间;因子接近 1 节省空位,却提高总复制量。渐近结论要求增长因子与 1 保持固定距离。

顺序数组去摊还化把一次整体复制分成固定预算的微步,按迁移前沿决定读写旧区或新区,并证明下一次扩容前完成。它在明确的分配成本模型下支持最坏常数的追加、读、写;迁移期间逻辑序列跨两块存储,因此不直接保留单一连续缓冲区接口。

参考资料
  • Thomas H. Cormen, Charles E. Leiserson, Ronald L. Rivest, and Clifford Stein, Introduction to Algorithms, 4th ed., MIT Press, 2022,§16.4, dynamic tables。
  • Erik D. Demaine, MIT 6.046J Design and Analysis of Algorithms, amortized analysis of dynamic-table expansion and contraction, accessed 2026.
关系图谱8 个相邻概念 · 3 类关系

拖动节点调整位置。

显示关系

显示:依赖

  1. 前置三跳
  2. 前置二跳
  3. 前置一跳
  4. 当前条目
  5. 后续一跳
  6. 后续二跳
  7. 后续三跳
文字版关系按与当前条目的最短距离分组
类型化关系

使用的工具

被这些条目使用

实现的抽象