effective stl 条款14:使用reverse来避免不必要的重新分配

vector 和 string:

1)自动增长的realloc内存操作

  1 分配新的内存块,它有容器目前容量的几倍。在大部分实现中,vector和string的容量每次以2为因数增
  长。也就是说,当容器必须扩展时,它们的容量每次翻倍。
  2 把所有元素从容器的旧内存拷贝到它的新内存。
    3 销毁旧内存中的对象。
    4 回收旧内存。

 由于分配,回收,拷贝,析构这些步骤都很昂贵,所以reverse函数。

eg:

//vector example
#include <iostream>
#include <vector>
using namespace std;

class Test
{
public:
    Test() { cout << "Test cons" << endl; }
    ~Test() { cout << "Test des" << endl; }
};

int main()
{
    vector<Test> vec;
    Test* p1 = new Test();
    Test* p2 = new Test();
    Test* p3 = new Test();
    // vec.reserve(3);     //加上此代码析构3次

    vec.push_back(*p1);
    vec.push_back(*p2);
    vec.push_back(*p3);

    //对象如何进行释放,要调用已定义析构函数  
    vec.clear();       //析构6次
    system("pause");
}

注意:resize 和 reserve的不同点:

// resizing vector
#include <iostream>
#include <vector>

int main ()
{
  std::vector<int> myvector;

  // set some initial content:
  for (int i=1;i<10;i++) myvector.push_back(i);

  myvector.resize(5);
  myvector.resize(8,100);
  myvector.resize(12);

  std::cout << "myvector contains:";
  for (int i=0;i<myvector.size();i++)
    std::cout << ' ' << myvector[i];
  std::cout << '\n';

  return 0;
}
myvector contains: 1 2 3 4 5 100 100 100 0 0 0 0
resize:强制把容器改为容纳n个元素。
调用resize之后,size将会返回n。如果n小于 当前大小,容器尾部的元素会被销毁。
如果n大于当前大小,新默认构造的元素会添加到容器尾部。 如果n大于当前容量,在元素加入之前会发生重新分配。
// vector::reserve
#include <iostream>
#include <vector>

int main ()
{
  std::vector<int>::size_type sz;

  std::vector<int> foo;
  sz = foo.capacity();
  std::cout << "making foo grow:\n";
  for (int i=0; i<100; ++i) {
    foo.push_back(i);
    if (sz!=foo.capacity()) {
      sz = foo.capacity();
      std::cout << "capacity changed: " << sz << '\n';
    }
  }

  std::vector<int> bar;
  sz = bar.capacity();
  bar.reserve(100);   // this is the only difference with foo above
  std::cout << "making bar grow:\n";
  for (int i=0; i<100; ++i) {
    bar.push_back(i);
    if (sz!=bar.capacity()) {
      sz = bar.capacity();
      std::cout << "capacity changed: " << sz << '\n';
    }
  }
  return 0;
}

making foo grow:
capacity changed: 1
capacity changed: 2
capacity changed: 4
capacity changed: 8
capacity changed: 16
capacity changed: 32
capacity changed: 64
capacity changed: 128
making bar grow:
capacity changed: 100

强制容器把它的容量改为至少n,提供的n不小于当前大小。这一般强迫
进行一次重新分配,因为容量需要增加。(如果n小于当前容量,vector忽略它,这个调用什么都不
做,string可能把它的容量减少为size()和n中大的数,但string的大小没有改变。

 

posted on 2017-08-02 16:55  123_123  阅读(293)  评论(0编辑  收藏  举报