C++-STL:vector用法总结
一、简介
vector,是同一类型的对象的集合,这一集合可看作可变大小的数组,是容器的一种。
- 对于容器来说,其重要特性之一便是于可以在运行时高效地添加元素。
- 类似于数组,vector采用连续内存地址来存储元素,因此vector属于顺序容器。也就意味着可以采用下标对vector的元素进行访问,和数组一样高效;同时它比数组更加灵活,它的大小(size)是可以动态改变的,且它的大小会被容器自动处理。
- vector分配空间策略:vector会分配一些额外的空间以适应可能的增长,使得分配的存储空间(capacity)比实际需要的存储空间更大。不同的库采用不同的策略权衡空间的使用和重新分配,vc里是每次增大当前capacity的一半。但是无论如何,重新分配总是对数增长的间隔大小,在末尾插入一个元素的时候则能够在常数时间的复杂度完成的。
- 在这里应理解好size与capacity之间的关系,这将有助于理解
vec.resize()与vec.reserve()的区别:- 容器的capacity是其size的上界,size总是<=capacity;当所需求的size>当前capacity时,vector便会如上文所述一般对capacity进行动态分配,以满足目标size需求。
- 我们使用
[]操作符时,只能访问size大小内的容器空间,这才是真正存在对象的内存空间;而>size同时<capacity的内存则属于“野”内存。
- 与其它动态序列容器相比(deques, lists and forward_lists), vector在访问元素的时候更加高效,在末尾添加和删除元素相对高效。对于其它不在末尾的删除和插入操作,效率更低。比起lists和forward_lists统一的迭代器和引用更好。
二、用法
1. 头文件
#include<vector>
2. vector的声明及初始化
(1)不带参数的构造函数初始化
// 初始化一个size为0的vector
vector<int> vec;
(2)带参数的构造函数初始化
仅指定vector大小,此时每个元素值为默认值0
vector<int> vec(10); //初始化了10个默认值为0的元素
指定vector大小和元素初始值
vector<int> vec(10,1); //初始化了10个值为1的元素
// 或是
vettor<int> vec = {1, 2, 3}; //初始化了1,2,3这3个元素
(3)通过同类型的vector初始化
vector<int> temp(5,1);
// 通过temp容器初始化一个元素相同的vec向量
vector<int> vec(temp);
通常来说,前三种便足够我们平时使用了。
(4)通过数组地址初始化
int a[5] = {1,2,3,4,5};
// 以数组a的元素初始化vector,注意地址是从0到5(左闭右开区间)
vector<int> vec(a, a+5);
(5)通过insert函数初始化
使用同类型的vector以及insert函数初始化
// insert初始化方式将同类型的迭代器对应的始末区间(左闭右开区间)内的值插入到vector中
vector<int> temp(6,6);
vecot<int> vec;
// 将temp[0]~a[2]插入到vec中,vec.size()由0变为3
vec.insert(vec.begin(), temp.begin(), temp.begin() + 3);
使用数组以及insert函数初始化
int a[6] = {6,6,6,6,6,6};
vector<int> vec;
// 将a的所有元素插入到vec中
vec.insert(vec.begin(), a, a+7);
通过insert函数添加m个值为n的元素
// 在vec开始位置处插入6个1
vec.insert(vec.begin(), 6, 1);
(6)通过copy函数赋值
vector<int> vec(5,1);
int a[5] = {2,2,2,2,2};
vector<int> target(10);
// 将vec中元素全部拷贝到target开始的位置中,注意拷贝的区间为vec.begin() ~ vec.end()的左闭右开的区间
copy(vec.begin(), vec.end(), target.begin());
// 拷贝区间也可以是由数组地址构成的区间
copy(a, a+5, vec.begin() + 5);
3. vector基本操作
1)容量相关
- 容器目前大小:
vec.size() - 容器目前容量:
vec.capacity() - 容器最大允许容量:
vec.max_size(); - 判断容器是否为空:
vec.empty() - 请求容器capacity减少至size大小:
vec.shrink_to_fit() - 更改容器容量:
vec.reverse(size_type n) - 更改容器大小
- 目标size小于当前size则截取前目标size个元素;大于则以元素填充存储空间至目标size
vec.resize(size_type n)仅指定size修改后大小n,需元素填充则以默认值0填充vec.resize(size_type n, value_type val)指定目标size大小n以及填充元素的值val
2)修改元素
- 末尾添加元素:
vec.push_back(value_type val) - 末尾删除元素:
vec.pop_back() - 对容器赋值:
vec.assign(const_iterator first, const_iterator last)将同类型容器目标区间[first, last)内的元素赋给调用者vec.assign(size_type n, const T& x = T())将n个x赋给调用者
- 在指定位置插入元素:
vec.insert(const_iterator position, value_type& val)在指定位置position插入元素valvec.insert(const_iterator position, size_type n, value_type& val)在指定位置position插入n个元素valvec.insert(const_iterator position, InputIterator first, InputIterator last)在指定位置插入同类型容器目标区间内的元素
- 在指定位置删除元素
vec.erase(const_iterator position)删除指定位置的素vec.erase(const_iterator first, const_iterator last)删除指定区间内的元素
- 与另一个容器交换元素:
vec.swap(vector& x) - 清空容器元素:
vec.clear()- 调用这个方法后,vec的size置为0但capacity不一定会重新分配
3)使用迭代器
- 声明迭代器(类似指针):
vector<size_type>::Iterator i- 访问迭代器指向的元素:
*i
- 访问迭代器指向的元素:
- 可写迭代器
- 指向容器开头:
vec.begin() - 指向容器结尾(指向最后一个元素再往后的一个内存):
vec.end()
- 指向容器开头:
- 只读迭代器(不能通过该指针来修改元素)
- 指向容器开头:
vec.cbegin() - 指向容器结尾:
vec.cend()
- 指向容器开头:
4)访问元素
- 访问指定位置元素。通过下面两个方法的比较可以看到,我们平时应优先使用
vec.at(i):vec[i]下标访问。不会下标检查是否越界,越界时返回一串无规律整形。vec.at(i)通过at函数访问。如果越界会抛出out of range的异常
- 访问第一个元素:
vec.front() - 访问最后一个元素:
vec.back() - 返回一个元素组成的数组的指针:
int* p = vec.data()
4. 常用操作
1)遍历元素
```
vector<int>::iterator it;
for (it = vec.begin(); it != vec.end(); it++) {
cout << *it << endl;
}
//或者
for (size_t i = 0; i < vec.size(); i++) {
cout << vec.at(i) << endl;
}
```
2)元素翻转
```
#include <algorithm>
reverse(vec.begin(), vec.end());
```
3)元素排序
```
#include <algorithm>
sort(vec.begin(), vec.end()); //采用的是从小到大的排序
//如果想从大到小排序,可以采用上面反转函数,也可以采用下面方法:
bool Comp(const int& a, const int& b) {
return a > b;
}
sort(vec.begin(), vec.end(), Comp);
```
文章最后,我个人认为头文件<algorithm>中的reverse()函数写得特别优雅,在此贴出源码
template <class BidirectionalIterator>
void reverse (BidirectionalIterator first, BidirectionalIterator last)
{
while ((first != last) && (first != --last)) {
std::iter_swap (first,last);
++first;
}
}
主要参考资料
C++-STL:vector用法总结的更多相关文章
- STL vector用法介绍
STL vector用法介绍 介绍 这篇文章的目的是为了介绍std::vector,如何恰当地使用它们的成员函数等操作.本文中还讨论了条件函数和函数指针在迭代算法中使用,如在remove_if()和f ...
- STL vector 用法介绍
介绍 这篇文章的目的是为了介绍std::vector,如何恰当地使用它们的成员函数等操作.本文中还讨论了条件函数和函数指针在迭代算法中使用,如在remove_if()和for_each()中的使用.通 ...
- STL:vector用法总结
一:介绍 vector是C++标准模板库,是一个容器,底层是数组,为连续内存.命名空间为std,所属头文件为<vector> 注意:不是<vector.h>vector存储 ...
- STL vector用法
基本操作 1.构造函数 vector():创建一个空vector vector(int nSize):创建一个vector,元素个数为nSize vector(int nSize,const t&am ...
- C++ stl vector介绍
转自: STL vector用法介绍 介绍 这篇文章的目的是为了介绍std::vector,如何恰当地使用它们的成员函数等操作.本文中还讨论了条件函数和函数指针在迭代算法中使用,如在remove_if ...
- stl——vector详解
stl——vector详解 stl——vector是应用最广泛的一种容器,类似于array,都将数据存储于连续空间中,支持随机访问.相对于array,vector对空间应用十分方便.高效,迭代器使ve ...
- 浅谈C++ STL vector 容器
浅谈C++ STL vector 容器 本篇随笔简单介绍一下\(C++STL\)中\(vector\)容器的使用方法和常见的使用技巧.\(vector\)容器是\(C++STL\)的一种比较基本的容器 ...
- C++ STL vector容器学习
STL(Standard Template Library)标准模板库是C++最重要的组成部分,它提供了一组表示容器.迭代器.函数对象和算法的模板.其中容器是存储类型相同的数据的结构(如vector, ...
- #include <vector>用法之我见
vector是一种顺序容器,事实上和数组差不多,但它比数组更优越.一般来说数组不能动态拓展,(何为动态拓展,即是说如果你知道你要存的数据的个数,你定义的存储数据的数组大小也就决定了,但是若你事先不知道 ...
随机推荐
- Oracle四舍五入,向上取整,向下取整
用oracle sql对数字进行操作: 取上取整.向下取整.保留N位小数.四舍五入.数字格式化 取整(向下取整): select floor(5.534) from dual; select trun ...
- ABAP术语-BOR (Business Object Repository )
BOR (Business Object Repository ) 原文:http://www.cnblogs.com/qiangsheng/archive/2007/12/25/1013523.ht ...
- PG进程结构和内存结构
本文主要介绍PostgreSQL数据库(后文简称PG)进程结构和内存结构,物理结构将在后续继续整理分享. 上图描述了PG进程结构.内存结构和部分物理结构的内容.图中的内容包含了两个部分: PG ...
- Hadoop(22)-Hadoop数据压缩
1.压缩概述 2.压缩策略和原则 3.MapReduce支持的压缩编码 64位系统下的单核i7,Snappy的压缩速率可以达到至少250MB/S,解压缩速率可以达到至少500MB/S 4.压缩方式选择 ...
- 数据分析处理库Pandas——时间
时间戳 向后推的时间戳 备注:五天后的时间. 指定日期和时间 时间的Series结构 按要求显示时间(开始时间,时间间隔,时间个数) 转换为时间格式,并设置时间列为索引列 方法一 方法二 筛选显示 方 ...
- 网站apache环境S2-057漏洞 利用POC 远程执行命令漏洞复现
S2-057漏洞,于2018年8月22日被曝出,该Struts2 057漏洞存在远程执行系统的命令,尤其使用linux系统,apache环境,影响范围较大,危害性较高,如果被攻击者利用直接提权到服务器 ...
- (数据科学学习手札13)K-medoids聚类算法原理简介&Python与R的实现
前几篇我们较为详细地介绍了K-means聚类法的实现方法和具体实战,这种方法虽然快速高效,是大规模数据聚类分析中首选的方法,但是它也有一些短板,比如在数据集中有脏数据时,由于其对每一个类的准则函数为平 ...
- AES128加密-S盒和逆S盒构造推导及代码实现
文档引用了<密码编码学与网络安全--原理和实践>里边的推导过程,如有不妥,请与我联系修改. 文档<FIPS 197>高级加密标准AES,里边有个S盒构造,涉及到了数论和有限域的 ...
- 9.Mongodb与python交互
1.与python交互 点击查看官方文档 安装python包 进入虚拟环境 sudo pip install pymongo 或源码安装 python setup.py 引入包pymongo impo ...
- Java:位移运算符
Java中有三个位移运算符,用于对int类型整数的二进制补码进行操作: 1. "<<": 左移运算符 在二进制补码末尾添加“0”,之前的其他位相当于左移了一位,可看作成 ...