C++ 笔记(23)— STL vector 类(实例化 vector、末尾插入、指定位置插入、数组方式访问元素、指针方式访问元素、删除元素、大小与容量区别)
1. vector 特点
vector
是一个模板类,提供了动态数组的通用功能,具有如下特点:
- 在数组末尾添加元素所需的时间是固定的,即在末尾插入元素的所需时间不随数组大小而异,在末尾删除元素也如此;
- 在数组中间添加或删除元素所需的时间与该元素后面的元素个数成正比;
- 存储的元素数是动态的,而
vector
类负责管理内存;
要使用 std::vector
类,需要包含下面的头文件:
#include <vector>
2. 实例化 vector
要实例化 vector
,需要指定要在该动态数组中存储的对象类型:
std::vector<int> i;
std::vector<float> f;
要声明指向 list
中元素的迭代器,可以这样做:
std::vector<int>::const_iterator elementInVec;
如果需要可用于修改值或调用非 const
函数的迭代器,可使用 iterator
代替 const_iterator
。
下面代码演示了几种实例化 vector
的方式:
#include <vector>
#include <iostream>using namespace std;void print(vector<int> vectorName)
{for(size_t i=0; i<vectorName.size(); i++){cout << vectorName[i] << endl;}
}int main ()
{vector<int> a; // 1. 默认构造函数实例化cout << "a.size() is " << a.size() << endl;vector<int> b {1,2,3}; // 2. 使用 c++ 11 列表初始化cout << "b.size() is " << b.size() << endl;print(b);vector<int> c (5); // 3. 初始化 vector 为 5 个元素cout << "c.size() is " << c.size() << endl;print(c);vector<int> d (3, 10); // 4. 初始化 vector 为 3 个元素,每个元素为 10cout << "c.size() is " << c.size() << endl;print(d);vector<int> e (d); // 5. 将 vector d 初始化为 e 的值cout << "e.size() is " << e.size() << endl;print(e);// 6. 初始化 f 为 5 个元素,并且是 vector d 的前 5 个元素vector<int> f (d.cbegin(), d.cbegin()+5);cout << "f.size() is " << f.size() << endl;print(f);return 0;
}
上述代码演示了如何为整型具体化 vector
类,即实例化一个存储整型数据的 vector
。该 vector
名为 a,它使用了默认构造函数,如第 16 行所示。在不知道容器最小需要多大,即不知道要存储多少个整数时,默认构造函数很有用。
3. 使用 push_back( )在末尾插入元素
在 vector
中插入元素时,元素将插入到数组末尾,这是使用成员函数 push_back()
完成的:
std::vector <int> a; // 声明一个 int 型的 vector
// 插入数据
a.push_back(50);
a.push_back(1);
完整示例:
int main ()
{std::vector<int> a; // 声明 vector astd::cout << "a.size() is " << a.size() << std::endl; // a.size() is 0a.push_back(10);a.push_back(5);a.push_back(1);std::cout << "a.size() is " << a.size() << std::endl; // a.size() is 3return 0;
}
4. 列表初始化
C++11
通过 std::initialize_list<>
支持列表初始化,让您能够像处理静态数组那样,在实例化 vector
的同时初始化其元素。与大多数容器一样, std::vector
也支持列表初始化,让您能够在实例化 vector
的同时指定其元素:
std::vector<int> a = {50, 1, 987, 1001};
// 或者
std::vector<int> a {50, 1, 987, 1001};
5. 使用 insert( )在指定位置插入元素
push_back()
在 vector
末尾插入元素。如果要在中间插入元素,可以使用 insert
。有以下几种插入方式:
- 插入指定的位置
vector<int> a;
a.insert(a.begin(), 25);
a.insert(a.begin()+2, 25);
- 指定插入位置、要插入的元素数以及这些元素的值(都相同)
a.insert (a.end(), 2, 45); // 插入两个元素均为 45 的值
- 将另一个
vector
的内容插入到指定位置:
vector <int> b (2, 30);
a.insert (a.begin() + 1, b.begin (), b.end ());
虽然函数 vector::insert()
用途广泛,但给 vector
添加元素时,应首选 push_back()
。这是因为将元素插入 vector
时, insert()
可能是效率最低的(插入位置不是末尾时),因为在开头或中间插入元素时,将导致 vector
类将后面的所有元素后移(为要插入的元素腾出空间)。
根据容器中包含的对象类型,这种移动操作可能需要调用复制构造函数或赋值运算符,因此开销可能很大。在上述例子中, vector
包含的是 int
对象,移动开销不是很大。但在其他情况下,情况可能并非如此。
注意:如果需要频繁地在容器中间插入元素,应选择 std::list
。
6. 使用数组语法访问 vector 中的元素
可使用下列方法访问 vector
的元素:
- 使用下标运算符
[]
以数组语法方式访问;
std::vector<int> tenElements (10);
// 可使用类似于数组的语法访问并设置各个元素:
tenElements[3] = 2011; for (size_t index = 0; index < integers.size(); ++index)
{cout << "Element[" << index << "] = " ;cout << integers[index] << endl;
}
- 使用成员函数
at()
;
// 获取索引为 2 的元素
cout << integers.at(2);cout << integers.at(index);
at()
函数在运行阶段检查容器的大小,如果索引超出边界(无论如何都不能这样做),将引发异常。
- 使用迭代器;
vector <int>::const_iterator element = integers.cbegin ();
7. 使用指针语法访问 vector 中的元素
vector <int> a (10);
vector <int>::const_iterator element = a.cbegin();
while (element != a.end ())
{size_t index = distance (a.cbegin(), element);cout << "Element at position ";cout << index << " is: " << *element << endl;// move to the next element++ element;
}
std::distance
来计算元素的偏移量(相对于开头的位置),这是根据 cbegin()
和指向元素的迭代器计算得到的。
8. 删除 vector 中的元素
除支持使用 push_back()
函数在末尾插入元素外, vector
还支持使用 pop_back()
函数将末尾的元素删除。使用 pop_back()
将元素从 vector
中删除所需的时间是固定的,即不随 vector
存储的元素个数而异。
vector <int> a (10);
a.pop_back(); // 删除最后一个元素
9. 大小与容量的区别
vector
的大小指的是实际存储的元素数,而 vector
的容量指的是在重新分配内存以存储更多元素前 vector
能够存储的元素数。因此, vector
的大小小于或等于容量。
- 要查询
vector
当前存储的元素数,可调用size()
:
cout << "Size: " << integers.size ();
- 要查询
vector
的容量,可调用capacity()
:
cout << "Capacity: " << integers.capacity () << endl;
10. 清空 vector 元素
要清空 vector
和 deque
等 STL
容器,即删除其包含的所有元素,可使用函数 clear()
。
integers.clear();
vector
和 deque
还包含成员函数 empty()
,这个函数在容器为空时返回 true
,而不像 clear()
那样删除既有的元素。
intDeque.clear();
if (intDeque.empty())
{cout << "The container is now empty" << endl;
}
C++ 笔记(23)— STL vector 类(实例化 vector、末尾插入、指定位置插入、数组方式访问元素、指针方式访问元素、删除元素、大小与容量区别)相关推荐
- C++std::vector指定位置插入
C++ std::vector指定位置插入 Bird鸟人 2017-09-05 19:31:47 24070 收藏 5 最后发布:2017-09-05 19:31:47首发:2017-09-05 19 ...
- [转载] C++ std::vector指定位置插入
参考链接: C++ : Vector删除所有指定的元素 使用vector,必须加上:#include <vector> 1.初始化vector,一般有这几种方式: std::vector& ...
- C++学习笔记(STL篇)string vector迭代器 stack queue
字符串基本操作 初始化string对象的方式: string s1 默认初始化,s1是一个空串 string s2(s1) s2是s1的副本 string s2 = s1 等价于s2(s1),s2是s ...
- 第七章:vector类
第七章:vector类 1.vector的介绍 vector的文档 ①vector是表示可变大小数组的序列容器. ②就像数组一样,vector也采用的连续存储空间来存储元素.也就是意味着可以采用下标对 ...
- STL容器之<vector>
文章目录 测试环境 vector介绍 头文件 模块类定义 对象构造 初始化 元素访问 元素插入和删除 容器大小 迭代器 其他函数 测试环境 系统:ubuntu 22.04.2 LTS 64位 gcc版 ...
- 黑马程序员--打印流、序列输入流、Vector 类
--------- android培训.java培训.期待与您交流! --------- 1 打印流 打印流: 该流提供了打印方法,可以将各种数据类型的数据都原样打印. 字节打印流: PrintStr ...
- STL源码剖析---vector
vector容器概述 vector的数据安排以及操作方式,与array非常相似.两者的唯一区别在于空间的运用的灵活性.array是静态空间,一旦配置了就不能改变:要换个大(或小)一点的房子 ...
- java的vector_java中的Vector类
public class Vector Vector 类实现了可动态扩充的对象数组.类似数组,它包含的元素可通过数组下标来访问.但是,在 Vector 创建之后.Vector 可根据增加和删除元素的需 ...
- java的vector是什么类_java中vector类
public class Vector extends 下列类的父类: Vector 类实现了可动态扩充的对象数组.类似数组,它包含的元素可通过数组下标来访问.但是,在 Vector创建之后.Vect ...
最新文章
- 测试录制的电话拨码声音信号在发送过程中的问题
- python培训学校-西安有没有好点的Python培训学校
- Hierarchical Attention Networks for Document Classification(HAN)
- php软件升级管理系统,POSCMS开源内容管理系统 v3.6.1 升级说明
- 程序员过关斩将--搞定秒杀,只需要这几步!!
- maven package install deploy区别
- java bufferedreader类_详解java中的BufferedReader类
- 在 Linux 下搭建 Git 服务器
- 告别ASP.NET操作EXCEL的烦恼(总结篇)(转)
- InputService
- centeros 卸载mysql_完全卸载MySql
- typora里插入图片,设置图片大小和位置
- html投影电脑,如何将电脑内容显示到投影仪或电视上?详细教程奉上
- mysql上线脚本规范_专业规范的mysql启停脚本
- How to write an exploratory essay
- 关于SSL认证的小坑 SSLPeerUnverifiedException
- mongodb 使用$lookup做多表关联处理
- 常用快递API(顺丰、EMS、申通、圆通等)及快递在线下单API分享
- 机械螺旋缠绕法管道非开挖修复
- websocket 发送数据大于0xFFFF(65535)的处理
热门文章
- 创建数据库,指定数据库的字符集和编码顺序
- 从风投看中国IT行业的发展
- RabbitMQ 入门系列(11)— RabbitMQ 常用的工作模式(simple模式、work模式、publish/subscribe模式、routing模式、topic模式)
- 107. Binary Tree Level Order Traversal II
- 垃圾回收 内存管理 python
- 从2012年到现在深度学习领域标志成果
- Python Re 模块超全解读!详细
- LeetCode简单题之最长和谐子序列
- nvGRAPH原理概述
- 广泛的信号处理链如何让语音助理“正常工作”