STL源碼分析之vector

Vector是序列容器的一種,分配的是一段連續的空間,所以它支持下標訪問,同時它另一特點是可以自行擴充空間,每次是以原大小兩倍來擴充,是另外配置的一塊空間,將原內容拷貝過去,所以當對vector的空間進行重新配置時,指向原vector的迭代器就失效了。下面分析它具體是怎麼實現的和熟悉下vector內部函數

  1. 迭代器

裏面主要有三個迭代器

iterator start;               // 表示目前使用空間的頭
iterator finish;              // 表示目前使用空間的尾
iterator end_of_storage;      // 表示vector可用空間的尾部

 

  1. 構造函數
vector() : start(0), finish(0), end_of_storage(0) {}


vector(size_type n, const T& value) { fill_initialize(n, value); }
vector(int n, const T& value) { fill_initialize(n, value); }
vector(long n, const T& value) { fill_initialize(n, value); }


explicit vector(size_type n) { fill_initialize(n, T()); } //加explicit防止發生隱式轉換

vector(const vector<T, Alloc>& x)
{
    start = allocate_and_copy(x.end() - x.begin(), x.begin(), x.end());
    finish = start + (x.end() - x.begin());
    end_of_storage = finish;
}

Vector有多種構造函數,可以看到它主要可以有一下幾種形式構造

Vector<int> ss(10,0)

Vector<int> ss(10)

Vector<int> ss(s) //拷貝構造,s是已初始化的vector對象

可以看到空間申請主要是用的fill_initialize函數


void fill_initialize(size_type n, const T& value) {
  start = allocate_and_fill(n, value);    
  finish = start + n;
  end_of_storage = finish;
}

可以看到它主要是調用了allocate_and_fill申請空間

iterator allocate_and_fill(size_type n, const T& x) {
  __STL_TRY {
    uninitialized_fill_n(result, n, x);    //初始化allocate分配的未初始化空間
    return result;
  }
  __STL_UNWIND(data_allocator::deallocate(result, n));    //失敗回收空間
}

3.一些特殊操作函數

 iterator begin() { return start; }  //獲取相應迭代器
    iterator end() { return finish; }

    // 返回當前對象個數
    size_type size() const { return size_type(end() - begin()); }
    size_type max_size() const { return size_type(-1) / sizeof(T); }
    size_type capacity() const { return size_type(end_of_storage - begin()); }
    bool empty() const { return begin() == end(); }    //是否爲空
    reference operator[](size_type n) { return *(begin() + n); }


    reference front() { return *begin(); }    //訪問元素
    reference back() { return *(end() - 1); }


void push_back(const T& x)
    {
        if (finish != end_of_storage)
        {
            construct(finish, x);    //,空間不滿足重新分配內存空間
            ++finish;
        }
        else
            insert_aux(end(), x);    //直接追加元素
    }


void pop_back()
    {
        --finish;
        destroy(finish);
    }

iterator erase(iterator position)
    {
        if (position + 1 != end())
            copy(position + 1, finish, position);
        --finish;
        destroy(finish);
        return position;
    }

 

發佈了36 篇原創文章 · 獲贊 15 · 訪問量 5936
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章