vector为变长数组,就是长度根据需要而自动改变的数组。通常在遇到普通数组超内存的情况下使用。vector还可以用来以邻接表的方式存储图,这对无法使用邻接矩阵的题目(结点数目过多)又不想用指针实现邻接表的人来说非常友好。
vector使用时需要添加头文件#include<vector>
。除此之外还要再头文件下加一句using namespace std;
。
vector的定义
单纯定义一个vector:
vector<typename> name;
这个定义相当于是一维数组name[SIZE],例如int、double、char、结构体等,也可以是STL标准容器,例如vector、set、queue等。如果是typename为STL容器时,定义的时候要在>>符号之间加上空格。(以免编译器视为移位操作)
vector<int> name;
vector<double> name;
vector<char> name;
vector<node> name; //node为结构体
如果typename是STL容器中的vector:
vector<vector<int> > name;
>> 之间加空格。写的时候很容易联想到二维数组,这是name[]中的每一个元素都是一个vector。可以简单地把二维vector数组看作是两个维都可以变长的二维数组来理解。
定义vector数组的方法:
vector<typename> arrayname[arraysize];
例如:
vector<int> vi[100];
这样arrayname[0] ~ arrayname[arraysize-1]中的每一个都是一个vector容器。
与vector<vector<int> >name;
不同的是,这种写法的一维长度已经固定位arraysize,另一维才是变长的。
vector容器内元素的访问
vector一般有两种访问方式:通过下标访问或通过迭代器访问。下面分别讨论着两种访问方式:
通过下标访问
和访问普通的数组一样,对一个定义为vector<typename> vi
的vector容器来说,直接访问vi[index]即可。当然,这里下标识从0到vi.size()-1,访问这个范围外的元素可能会运行出错。
通过迭代器访问
迭代器定位为:
vector<typename>::iterator it;
这样it就是一个vector<typename>::iterator
类型的变量,其中typename就是定义vector时填写的类型。可以就得到了迭代器it,可以通过*it来访问vector中的元素。
//定义一个vector
vector<int> vi;
for(int i =1;i<=5;i++){
vi.push_back(i); //添加元素
}
//通过迭代器访问vector
//vi.begin()为取vi的首元素地址,而it指向这个地址
vector<int>::iterator it = vi.begin();
for(int i =0;i<5;i++){
printf("%d ", *(it+i)); //输出vi[i]
}
vi[i] 和 *(vi.begin()+i)等价。
vi.begin()为取首元素地址,vi.end()为取尾元素地址的下一个地址。(左闭右开)
同时迭代器可以实现: ++it和it++,所以遍历元素的另一种写法:
for(vector<int>::iterator it = vi.begin();it!=vi.end();it++){
printf("%d ",*it);
}
在STL容器中,只有vector和string允许使用vi.begin()+4这种迭代器+整数的写法。
vector的常用函数
- push_back()
push_back(x)就是在vector后面添加一个元素x。
- pop_back()
pop_back(x)用以删除vector的尾元素。
- size()
size()用来获得vector中元素的个数。
- clear()
clear()用来清空vector中的所有元素。
- insert()
insert(it, x)用来向vector的任意迭代器it处插入一个元素x。
vi.insert(vi.begin()+2,-1);
- erase()
erase()有两种用法,①删除单个元素;②删除一个区间内的所有元素。
① 删除单个元素:erase(it),删除迭代器处的元素
② 删除一个区间内的所有元素:erase(first,last),即删除[first,last )区间内的元素。
vector的常见用途
- 存储数据。在元素个数不确定的时候可以使用它作为数组。
- 用邻接表存储图。用vector实现邻接表。