1. 程式人生 > >2.3 動態空間管理

2.3 動態空間管理

動態空間 操作系統 nbsp 強烈 系統 期望 sun cto i++

空間管理方法主要分為兩類:靜態的和動態的。顧名思義,靜態空間管理即是在向量生命期內,其內部數組所占物理空間的容量不允許增加,這種策略既拘泥固化且空間管理效率底下,因此常采取動態空間管理策略,具體方法是使向量可擴充。 可擴充向量既能夠在空間不足達到上溢臨界點時擴充向量空間,同時能夠在空間需求不甚強烈,達到下溢臨界點時縮容空間向量。 擴容 對向量實現擴容的難點在於如何實現擴容?新的容量取作多少才算適宜? 如何擴容?——先保留,再擴容,後遷移。 因為向量是尋秩訪問,上下秩之間物理地址連續,所以在擴容的過程中必須保證物理空間必須地址連續,所以可行的方法是:通過申請更大容量的內部數組,將原先內部數組中的成員集體搬遷到新的空間,此後方可順利地插入新元素e而不致數據溢出。原數組所占空間及時釋放,並歸還操作系統。實現代碼如下: template <typename T> void Vector<T>::expand() {
if (_size < _capacity) return; if (_capacity < DEFAYLT_CAPACITY) _capacity = DEFAYLT_CAPACITY;//使其不小於默認容量即最小容量 T* oldElem = _elem; _elem = new T[_capacity <<= 1];//容量加倍 for (int i = 0; i < _size; i++) _elem[i] = oldElem[i];//復制原向量內容
delete[] oldElem; } 有趣的是,最調用insert()接口插入新元素之前,都要先調用該算法用於檢查數組容量。 縮容 當向量的規模遠遠小於內部數組的容量,稱為下溢時,我們會采取縮容操作。具體算法如下: template <typename T> void Vector<T>::shrink() { if (_capacity < DEFAYLT_CAPACITY << ) return; if (_size << 2 > _capacity)
return; T* oldElem = _elem; _elem = new T[_capacity >>= 1];//容量加倍 for (int i = 0; i < _size; i++) _elem[i] = oldElem[i];//復制原向量內容 delete[] oldElem; } 當我們分析通過直接擴容兩倍的方式來分析擴容向量復雜度時,采取的具體尺度是分攤復雜度。 所謂分攤復雜度和相關的分攤運行時間,其參與分攤的操作必須構成和來自一個真實可行的操作序列,且足夠長。這與傳統的平均運行時間有著本質的區別,後者是按照某種假定的概率分布,對各種情況下所需執行時間的加權平均,亦稱期望運行時間。 對於本文中所采取的兩倍擴容操作,所需時間為O(n)。

2.3 動態空間管理