STL学习笔记-- vector

vector 向量容器

    作为数组的一个泛化推广的 vector 容器,不仅可以进行数组一样的元素随机访问,还可以在容器的尾端插入新元素,是一个实现了 Random Access Container 和 Back Insertion Sequence 概念的模型 
    vector 是一种简单、高效的容器。在尾端插入和删除元素,算法时间复杂度为 O(1) 常数阶,其他元素的插入删除为 O(n) 线型阶,其中 n 为 vector 容器的元素个数。 vector 具有自动的内存管理功能,对于元素的插入和删除,可动态调整所占用的内存空间。

    vector 容器的 C++ 标准头文件为 vector, 因此,必须将宏语句 "#include <vector>" 包含到cpp文件中,才可正确编译使用。



创建 vector 对象
如下4个vector的构造函数,均可创建一个vector对象
1.    vector(const A& a = A())
    创建一个空的 vector 对象,A 是内存分配器,此参数可以省略,相当于一个 vector() 的调用。
例如,下面一行代码创建了一个 vector 对象 vInt
    vector<int>  vInt;  

2.    vector(size_type n)
     创建一个具有 n 个元素的 vector 对象,每个 vector 元素具有它的类型下的默认值。此时, n 个 vector 元素的内存空间已被分配。
例如,下面一行代码创建了具有 10 个元素的 vector 对象 vDou,每个元素的默认值为 0.0
    vector<double>  vDou(10);
    
3.    vector(size_type n, const T& value)
    创建一个具有 n 个元素的 vector 对象,每个元素具有初始值 value 。
例如,下面一行代码创建了一个具有 10 个元素的 vector 对象 vDou, 每个元素的初始值为 9.3
    vector<double>  vDou(10, 9.3);
    
4.    vector(const vector&)
    通过拷贝一个 vector 对象的各个元素值,创建一个新的 vector 对象。
例如,下面使用 v1 对象 创建 v2 对象,此时,v2 对象的 5 个元素也具有字符值 "K"
    vector<char>  v1(5,'K');
    vector<char>  v2(v1);

这是第五种创建方法   
5.    vector(const InputInerator first, const InputIterator last, const A& a = A())
    InputIterator 为输入迭代器,通过拷贝迭代器区间 [first, last ) 的元素值,创建一个新的vector对象,内存分配器可省略。
例如,利用 int 数组 iArray 各元素值,创建了 vector 对象 v
    int iArray[] = {11, 13, 19, 23, 28};
    vector<int>  v(iArray, iArray + 5);

 1 // 创建对象之后,再赋值的方法,  assign 函数
 2 vector<int> vecIntA, vecIntB, vecIntC;
 3 int  iArray[] = {0,1,2,3,4};
 4 vecIntA.assign(iArray,iArray+5);
 5 
 6 vecIntB.assign( vecIntA.begin(),  vecIntA.end() );    //用其它容器的迭代器作参数。
 7 
 8 vecIntC.assign(3,9);  // 在对象vecIntC中添加 3 个元素,元素值值为 9
 9 
10 vector<int> vecIntD;  // 直接赋值也可以,这是深拷贝,赋值之后,vecIntA 中的值改变,不会影响vecIntD
11 vecIntD = vecIntA;

 




初始化赋值
vector 提供的 push_back() 函数,常用来进行 vector 容器的初始化。 push_back() 函数在容器的尾端插入新元素。


元素的遍历访问
 vector 的元素可以采用数组,.at() 函数或者迭代器的方式进行遍历访问。

 

用数组方式访问 vector 元素
 1 #include <vector>
 2 #include <iostream>
 3 using namespace std;
 4 int main()
 5 {
 6     vector<int> vInt;
 7     vInt.push_back(20);
 8     vInt.push_back(26);
 9     vInt.push_back(39);
10     
11 //    cout << "VInt【2】 = " << vInt[2] <<endl;
12 //    cout << "VInt【3】 = " << vInt[3] <<endl;
13 //    cout << "VInt【4】 = " << vInt[4] <<endl << endl << endl;
14 //    
15 //    cout << "VInt【2】 = " << vInt.at(2) <<endl;    
16 //    cout << "VInt【3】 = " << vInt.at(3) <<endl;
17 //    cout << "VInt【4】 = " << vInt.at(4) <<endl;
18     
19 
20     for (int i=0; i<vInt.size(); i++)
21     {
22         // vInt[i] 为数组方式的访问。访问越界时,不产生异常
23         //cout << "VInt【" << i << "】 = " << vInt[i] <<endl;
24         
25         // vInt.at(i) 为函数访问方式。当访问越界时,会抛出异常
26         cout << "VInt【" << i << "】 = " << vInt.at(i) <<endl;
27     }
28 
29 
30     return 0;
31 }

 

 

用迭代器访问 vector 元素
 1 #include <vector>
 2 #include <iostream>
 3 using namespace std;
 4 int main()
 5 {
 6     vector<int> vInt;
 7     vInt.push_back(20);
 8     vInt.push_back(26);
 9     vInt.push_back(39);
10 
11     // 起始 和 末尾 迭代器值 
12     vector<int>::iterator i, iend;
13     iend = vInt.end();
14     int j;
15     for (i=vInt.begin(), j=0; i!=iend; i++, j++)
16     {
17         cout << "v[" << j << "] = " << *i << endl;
18     }
19 
20     return 0;
21 }

 

 

在任意位置插入 vector 元素
 1 /*        解释:
 2     不同于在 vector 容器尾部添加元素的 push_back 函数, insert 函数可以在任意位置插入元素。
 3 由于插入时,需要先将插入位置后面的元素移位,以空出一个位置进行插入,因此,insert 函数的执行比较 push_back 函数较为耗时。
 4 */
 5 
 6 -------------------------------- 在任意位置插入 vector 元素
 7 #include <vector>
 8 #include <iostream>
 9 using namespace std;
10 int main()
11 {
12     vector<int> vInt;
13     vInt.push_back(6);
14     vInt.push_back(7);
15     vInt.push_back(8);
16     vInt.push_back(10);
17     // 在元素 10 的前面插入 9
18     vInt.insert(vInt.begin() + 3, 9);
19     // 插入 5 为首元素
20     vInt.insert(vInt.begin(), 5);
21     // 插入 11 为末元素
22     vInt.insert(vInt.end(), 11);
23 
24     for (int i=0; i<vInt.size(); i++)
25     {
26         cout << "V[" << i << "]=" << vInt[i] << endl;
27     }
28 
29     return 0;
30 }

 

 

 

利用 erase 函数删除 vector 元素
 1 ---------------------------------------- 利用 erase 函数删除 vector 元素
 2 #include <iostream>
 3 #include <vector>
 4 using namespace std;
 5 class MyAnimal
 6 {
 7 public:
 8     char* m_name;
 9     int m_age;
10 public:
11     MyAnimal(char* name, int age)
12     {
13         this->m_name = name;
14         this->m_age = age;
15     }
16     ~MyAnimal(){}
17 
18 };
19 
20 int main()
21 {
22     MyAnimal* pDog = new MyAnimal("dog", 1);
23     MyAnimal* pMonkey = new MyAnimal("monkey", 2);
24     MyAnimal* pChicken = new MyAnimal("chicken", 3);
25     MyAnimal* pSnake = new MyAnimal("snake", 4);
26 
27     // v 将存放各对象的地址
28     vector<MyAnimal*> v;
29     v.push_back(pDog);
30     v.push_back(pMonkey);
31     v.push_back(pChicken);
32     v.push_back(pSnake);
33 
34     // 物理删除 pMonkey 所指的对象
35     delete pMonkey;
36     // 删除第 2 个元素,即删除 vector 容器的元素 pMonkey
37     v.erase(v.begin()+1);
38     vector<MyAnimal*>::iterator i, iend;
39     iend = v.end();
40     for (i=v.begin(); i!=iend; ++i)
41     {
42         cout << (*i)->m_name << ' ' << (*i)->m_age <<endl;
43     }
44     // 清除所有 vector 元素
45     v.clear();
46     cout << " 执行 clear() " << endl << "vector 元素已全部清除。" <<endl;
47 
48     return 0;
49 }

 

erase 的补充
 1 -------- erase 的补充
 2  vecInt是用vector<int>声明的容器,现已包含按顺序的1,3,2,3,3,3,4,3,5,3元素。现要求删除容器中所有等于3的元素。
 3 for(vector<int>::iterator it=vecInt.begin(); it!=vecInt.end(); )    //小括号里不需写  ++it
 4 {
 5     if(*it == 3)
 6    {
 7         it  =  vecInt.erase(it);       //以迭代器为参数,删除元素3,并把数据删除后的下一个元素位置返回给迭代器。
 8          //此时,不执行  ++it;  
 9    }
10     else
11    {
12        ++it;
13    }
14 }

 

 

 

反向遍历 vector 的元素
 1 -------------------------------------------------- 反向遍历 vector 的元素
 2 #include <vector>
 3 #include <iostream>
 4 using namespace std;
 5 int main()
 6 {
 7     vector<int> vInt;
 8     vInt.push_back(1);
 9     vInt.push_back(3);
10     vInt.push_back(5);
11     vInt.push_back(7);
12     vInt.push_back(9);
13     // 元素的反向遍历访问
14     vector<int>::reverse_iterator ri,riend;
15     riend = vInt.rend();
16     for (ri=vInt.rbegin(); ri!=riend; ++ri)
17     {
18         cout << *ri << endl;
19     }
20 
21     return 0;
22 }

 

 

两个 vector 容器元素的交换
 1 -------------------------------------------------- 两个 vector 容器元素的交换
 2 #include <vector>
 3 #include <iostream>
 4 using namespace std;
 5 void print(vector<int>& vInt);
 6 int main()
 7 {
 8     //vIntA
 9     vector<int> vIntA;
10     vIntA.push_back(11);
11     vIntA.push_back(12);
12     vIntA.push_back(13);
13     cout << " vIntA = ";
14     print(vIntA);
15 
16     //vIntB
17     vector<int> vIntB;
18     vIntB.push_back(90);
19     vIntB.push_back(92);
20     cout<< " vIntB = ";
21     print(vIntB);
22 
23     // vIntA 与 vIntB 交换
24     swap(vIntA, vIntB);
25     cout << "vIntA 与 vIntB 交换后" << endl;
26     cout << "vIntA =";
27     print(vIntA);
28     cout << "vIntB =";
29     print(vIntB);
30 
31     return 0;
32 }
33 
34 // vector 元素打印
35 void print(vector<int>& v)
36 {
37     for (int i=0; i<v.size(); i++)
38         cout<< v[i] << "  " ;
39     cout << endl;
40 }

 

 

vector 的其他常用函数
 1 /*        解释:
 2 1. bool empty()  判断容器 vector 是否为空,若容器没有一个元素则返回 true, 否则返回 false
 3 2. size_type size()  当前 vector 容器的实际元素个数
 4 3. size_type max_size()  系统所允许的 vector 容器的最大元素个数
 5 4. size_type capacity()  当前可容纳的 vector 元素个数
 6 5. reference front()  vector容器的首元素(引用),要求 vector 不为空
 7 6. reference back()  vector容器的末元素(引用),要求 vector 不为空
 8 7. void pop_back()  与 push_back() 函数相反,pop_back() 函数用于删除末尾的一个容器元素
 9 */
10 
11 -------------------------------- vector 的其他常用函数
12 #include <vector>
13 #include <iostream>
14 using namespace std;
15 void print(vector<int>& v);
16 int main()
17 {
18     vector<int> vInt;
19     print(vInt);
20     // 添加 5 个元素
21     vInt.push_back(1);
22     vInt.push_back(2);
23     vInt.push_back(3);
24     vInt.push_back(4);
25     vInt.push_back(5);
26     print(vInt);
27 
28     // 再添加 4 个元素
29     vInt.push_back(6);
30     vInt.push_back(7);
31     vInt.push_back(8);
32     vInt.push_back(9);
33     print(vInt);
34 
35     // 调整 vector 数据空间大小
36     vInt.reserve(30);
37     print(vInt);
38 
39     return 0;
40 }
41 
42 void print(vector<int>& v)
43 {
44     cout << "----------------------" << endl;
45     cout << "empty = " << v.empty()<< endl;
46     cout << "size = " << v.size()<< endl;
47     cout << "max_size = " << v.max_size()<< endl;
48     cout << "capacity = " << v.capacity()<< endl;
49 
50 }

 

 

 

 

------------ vector 小结:
    vector 向量容器是一个实现数据线型存储的泛型类,除了可以使用数组方式进行元素访问外,还可以利用前向和反向迭代器
iterator/reverse_iterator ,以及 push_back 、 begin 、 end 、 erase 和 clear 等函数,对容器元素进行插入、遍历和删除操作。
  vector尾部添加或移除元素非常快速。但是在中部或头部插入元素或移除元素比较费时


    vector 缺点: vector 不适合那种 【容器元素在任意位置进行  插入、删除 操作非常频繁】 的情况
    vector 优点: 看最前面的介绍

 

 

 

 

 

posted @ 2013-04-03 19:50  He_LiangLiang  阅读(1987)  评论(1编辑  收藏  举报