文章目录

  • empty()和size()都可以判断容器是否为空,谁更好?
  • array 为何比 普通数组 安全
  • vector容器的 容量(capacity)和 大小(size)的区别
  • vector添加元素push_back()和emplace_back()的区别
  • vector插入元素insert()和emplace()的区别
  • vecter容器使用remove()需要注意:
  • 为何要避免使用vector
  • deque容器为什么没有提供data()成员函数 ( 为何不要使用指针去访问deque容器中指定位置处的元素 )
  • forward_list没有size()成员函数,如何获取元素个数

empty()和size()都可以判断容器是否为空,谁更好?

建议使用 empty() 成员方法。理由很简单,无论是哪种容器,只要其模板类中提供了 empty() 成员方法,使用此方法都可以保证在 O(1) 时间复杂度内完成对“容器是否为空”的判断;但对于 list 容器来说,使用 size() 成员方法判断“容器是否为空”,可能要消耗 O(n) 的时间复杂度。
此处参考

array 为何比 普通数组 安全

普通数组没有做任何边界检查,所以即便使用越界的索引值去访问或存储元素,也不会被检测到
例如:

int test2[10] = { 1,2,3,4,5 };
test2[4] = 2.0 * test2[111];
std::cout << test2[4] << std::endl;

注意:array 这样使用也不会被检测到

std::array<int, 10> test{ 1,2,3,4,5 };
test[4] = 2.0 * test[111];
std::cout << test[4] << std::endl;

为了能够有效地避免越界访问的情况,可以使用 array 容器提供的 at() 成员函数,例如 :

std::array<int, 10> test{ 1,2,3,4,5 };
test.at(4) = 2.0 * test.at(111);
std::cout << test[4] << std::endl;

vector容器的 容量(capacity)和 大小(size)的区别

vector 容器的容量(用 capacity 表示),指的是在不分配更多内存的情况下,容器可以保存的最多元素个数;而 vector 容器的大小(用 size 表示),指的是它实际所包含的元素个数。

注意: 当 vector 容器的大小和容量相等时,如果再向其添加(或者插入)一个元素,vector 往往会申请多个存储空间,而不仅仅只申请 1 个,并且容器会重新生成。
例:

int main() {std::vector<int>test{ 1,2,3,4,5 };std::cout << "test 容量是:" << test.capacity() << std::endl;std::cout << "test 大小是:" << test.size() << std::endl;std::cout << "test首地址:" <<test.data() << std::endl;test.push_back(6);std::cout << "test 容量是(2):" << test.capacity() << std::endl;std::cout << "test 大小是(2):" << test.size() << std::endl;std::cout << "test首地址:" << test.data() << std::endl;test.push_back(7);std::cout << "test 容量是(2):" << test.capacity() << std::endl;std::cout << "test 大小是(2):" << test.size() << std::endl;std::cout << "test首地址:" << test.data() << std::endl;
}

结果:

test 容量是:5
test 大小是:5
test首地址:00000237D6E200E0
test 容量是(2):7
test 大小是(2):6
test首地址:00000237D6E1D320
test 容量是(2):7
test 大小是(2):7
test首地址:00000237D6E1D320

可见当容器的大小超过容器的容量的时候,容器的首地址改变了,说明容器重建了

注意:当 vector 容器的大小和容量相等时,向其添加一个元素时会使得首地址发生改变。(经常有人因此发生bug,需要注意)

vector内部的扩容步骤:

  1. 弃用现有的内存空间,重新申请更大的内存空间;
  2. 将旧内存空间中的数据,按原有顺序移动到新的内存空间中;
  3. 将旧的内存空间释放。

vector添加元素push_back()和emplace_back()的区别

emplace_back() 和 push_back() 的区别,就在于底层实现的机制不同。push_back() 向容器尾部添加元素时,首先会创建这个元素,然后再将这个元素拷贝或者移动到容器中(如果是拷贝的话,事后会自行销毁先前创建的这个元素);而 emplace_back() 在实现时,则是直接在容器尾部创建这个元素,省去了拷贝或移动元素的过程。
简而言之:emplace_back()是c++11 新添加的,效率要比push_back()高

vector插入元素insert()和emplace()的区别

语法格式 用法说明
iterator insert(pos,elem) 在迭代器 pos 指定的位置之前插入一个新元素elem,并返回表示新插入元素位置的迭代器。
iterator insert(pos,n,elem) 在迭代器 pos 指定的位置之前插入 n 个元素 elem,并返回表示第一个新插入元素位置的迭代器。
iterator insert(pos,first,last) 在迭代器 pos 指定的位置之前,插入其他容器(不仅限于vector)中位于 [first,last) 区域的所有元素,并返回表示第一个新插入元素位置的迭代器。
iterator insert(pos,initlist) 在迭代器 pos 指定的位置之前,插入初始化列表(用大括号{}括起来的多个元素,中间有逗号隔开)中所有的元素,并返回表示第一个新插入元素位置的迭代器。
iterator emplace (pos, elem) 在迭代器 pos 指定的位置之前插入一个新元素elem,并返回表示新插入元素位置的迭代器。

可见:insert() 的功能要比 emplace()多。单比较插入一个元素,emplace()效率要比insert()要高,原因同上一条。

vecter容器使用remove()需要注意:

注意: remove()不是vector的成员函数,该函数定义在 头文件中

通过remove()函数删除 vector容器中的多个指定元素,该容器的大小和容量都没有改变,其剩余位置还保留了之前存储的元素,还需要使用 erase() 成员函数删掉这些无用的元素。
如图:

例子:

int main() {std::vector<int>test{ 9,9,9,1,2,3,4,5,6,7,8,9 };std::cout << "size:"<< test.size() << std::endl;std::cout << "capacity:" << test.capacity() << std::endl;for (auto i : test) {printf(" %d", i);}printf("\n");auto iter = std::remove(test.begin(), test.end(), 9);for (auto i : test) {printf(" %d", i);}printf("\n");std::cout << "size:" << test.size() << std::endl;std::cout << "capacity:" << test.capacity() << std::endl;test.erase(iter, test.end());for (auto i : test) {printf(" %d", i);}printf("\n");std::cout << "size:" << test.size() << std::endl;std::cout << "capacity:" << test.capacity() << std::endl;
}

结果:

size:12
capacity:129 9 9 1 2 3 4 5 6 7 8 91 2 3 4 5 6 7 8 6 7 8 9
size:12
capacity:121 2 3 4 5 6 7 8
size:8
capacity:12

为何要避免使用vector

这是个c++ 的历史遗留问题,在早先vector每个元素是存在一个bit中而不是byte。
且vector 不完全满足 C++ 标准中对容器的要求,
所以vector就不是一个容器,尽量避免在实际场景中使用它!
在需要用到的时候用 deque 代替

deque容器为什么没有提供data()成员函数 ( 为何不要使用指针去访问deque容器中指定位置处的元素 )

和vector不同,deque的存储空间不一定是连续的,通常他是有多个连续的空间组成的。因此尝试使用指针去访问 deque 容器中指定位置处的元素,是非常危险的

deque的存储方式如下图所示:

forward_list没有size()成员函数,如何获取元素个数

可以使用头文件 中的 distance() 函数

#include <iostream>
#include <forward_list>
#include <iterator>
int main()
{std::forward_list<int> test{1,2,3,4,5,6,7,8,9,10};int size = std::distance(test.begin(), test.end());int size2 = std::distance(std::begin(test), std::end(test));std::cout << "size:" << size << std::endl;std::cout << "size2:" << size2 << std::endl;
}
size:10
size2:10

SLT容器使用技巧以及注意事项相关推荐

  1. PCB设计要点-DDR3布局布线技巧及注意事项

    前面高速先生已经讲解过众多的DDR3理论和仿真知识,下面就开始谈谈我们LATOUT攻城狮对DDR3设计那些事情了,那么布局自然是首当其冲了. 对于DDR3的布局我们首先需要确认芯片是否支持FLY-BY ...

  2. MySQL索引类型总结和使用技巧以及注意事项

    在数据库表中,对字段建立索引可以大大提高查询速度.假如我们创建了一个 mytable表: 复制代码代码如下: CREATE TABLE mytable(   ID INT NOT NULL,    u ...

  3. linux中paste的用法,在Linux中使用Paste命令来合并行,包括使用Paste命令技巧及注意事项...

    在本文中,我们将教你如何使用Paste命令,包括使用Paste命令技巧及注意事项.Paste是允许你水平合并文件行的命令,它输出由指定为参数的每个文件的顺序对应的行组成的行,并用制表符分隔. 如何使用 ...

  4. 外文翻译原文附在后面_劳动合同翻译都有哪些技巧和注意事项?

    随着中国与全球方式的转变与"一带一路"合作倡议的落实推进,我国对外投资合作规模不断扩大,每年赴境外的人员数量增幅加大,国外国外务工所面临的国际形势日趋复杂多变那么对按翻译需求也将剧 ...

  5. 定性研究的小技巧与注意事项!

    最近几个月,做了好几个定性研究的项目:事后做录音整理时,越发觉得6月初在北京参加"定性座谈会主持"培训课程中学习到的内容,是多么有价值!真是对实践的理论化,理论知识的实践化. 在这 ...

  6. 大学生面试技巧与注意事项|实战经验

    据市场调查企业对应届生的要求大多为:实际能力较强,做事踏实,有上进心,有明确的职业规划. 学生拔不拔尖并不是最重要的,最主要是要有强烈的进取心,接受能力快,做事踏实稳重,有明确的发展方向,能找准自己的 ...

  7. 单招计算机面试技巧和注意事项,单招面试技巧和注意事项

    有哪些细节是单招面试的时候需要注意的呢?下面是由学习啦小编分享的单招面试技巧和注意事项,希望对你有用. 单招面试技巧之自我介绍 在高职单招面试时怎样进行自我介绍呢?对于很多缺乏社会交往经验的人来说,要 ...

  8. 玉米社:网站seo站外优化技巧、注意事项

    网站seo站外优化技巧.注意事项. 1.不与添加nofollow属性的友链进行交换 nofollow属性旨在告诉搜索引擎,不要对该链接进行抓取追踪和权重传递,原本,友情链接是网站交换双方权重的双向传递 ...

  9. 英文连写字体怎么练_衡水体英文字体,你必须知道的技巧和注意事项!(建议收藏)...

    作文要想得高分,没有让阅卷老师"一见钟情"的卷面怎么行????? 在英文书写方面,大多人首推"衡水体".它的特点是圆润,饱满,字母的高度,大小,间距,单词间距都 ...

  10. 计算机专业进中国移动难吗,【计算机】中国移动面试技巧和注意事项

    [计算机]中国移动面试技巧和注意事项 1.面试的时候紧张怎么办? 考生紧张多是由于应试者的卑怯心理和求胜心切而造成的.因此,考生一进面试室,应该去掉"自愧不如人"的意识,确立&qu ...

最新文章

  1. mongodb清洗数据
  2. 音视频技术开发周刊 | 213
  3. java中矩阵怎么打印_在Java编程中打印二维数组或矩阵
  4. VS2005的几款代码皮肤。
  5. python 读取redis数据后转为dataframe格式数据
  6. WPF如何给窗口设置透明png的图片背景
  7. 两年前端菜鸟回忆篇(1)
  8. 禁用ViewPager边界滑动效果(转)
  9. 7个现象告诉你手游圈为什么会有寒冬
  10. 数据结构(二)之二叉树
  11. 重构Webpack系列之四 ---- Loaders
  12. Windows与ipad共享文件
  13. Android开发 人民币符号(¥)显示不一致的问题
  14. java对接 布防 海康威视_java调用海康威视sdk获取车牌号demo
  15. 埋点 神策小程序_神策埋点思路
  16. Android Wifi P2P 入门
  17. python画英国国旗_python ASCII艺术英国国旗
  18. 杭州人才补助领取遇到的问题
  19. huaweicloud华为云-云通信-语音通话对接文档整理
  20. STM32直流减速电机控制篇(一)PWM调速

热门文章

  1. 【信息检索导论】第一章 布尔检索
  2. 【第四篇】用 Qt 实现电子白板
  3. Docker桥存储卷管理
  4. javaSE 打印流,PrintWriter,PrintStream。 打印到输出流(文件)中
  5. 实对称矩阵的若干性质与详细证明
  6. 谜底是计算机病毒的谜语,有关于安全的谜语及谜底答案解析|谜底是粽子的谜语...
  7. Java女生后来_那些主动的女生后来怎么样了?
  8. linux字体不识别不了怎么办,Docker容器不识别宋体等字体怎么办
  9. 凯文·凯利写给年轻人的99条人生建议(99 Additional Bits of Unsolicited Advice)
  10. 传奇服务器赞助文件夹,传奇服务端每个文件夹的含义