博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
STL中的Vector
阅读量:4255 次
发布时间:2019-05-26

本文共 1337 字,大约阅读时间需要 4 分钟。

看了一下vector的实现,感觉C++的内存管理,确实是需要非常认真对待的。

为了追求效率,自身就需要仔细万分,总结了3,4点感觉尤其如此。

1.vector的底层实现

这个倒是很简单,vector就是一段动态分配内存的数组,加上冗余空间,所以用三个指针(迭代器)就能表示出来,底层的数据结构。

分别是迭代器:start、finish、end_of_storage

其中,finish-start=size,end_of_storage-start=capacity

2.vector的一系列操作

(1)增

push_back<---------->emplace_back

insert<------------------>emplace

emplace是通过填入参数,然后调用其他构造函数,构造对象

push和insert是调用拷贝构造函数构造对象

(2)删

pop_back

erase

clear

注意:只有对中间操作的函数才有返回值,且返回值为iterator。

比如,insert、emplace、erase

最最复杂的操作应该就是insert操作了。

3.copy和copy_backward

copy(first, end, result)

将从first到end的对象拷贝到,result开始的一段内存区域。

顺序为:first--》result, first+1--》result+1,。。。, first+(end-first-1)--》result+(end-first-1)

copy_backward(first, end, result)

顺序为:end-1--》result-1, end-2--》result-2, 。。。, first--》resutl-(end-first+1)

注意:由于不管是copy还是copy_backward都是一个一个移动的,所以当用copy向右移动,且移动长度小于要移动的序列长度时,有坑,会覆盖。

当copy_backward向左移动,且移动长度,小于要移动的序列长度时,有坑,会覆盖。

4.copy和uninitialized_copy

这个问题我发现了,后来到知乎上去看,别人也有同样的疑问:

简单来说,就是copy和uninitialized_copy的区别。

前者假设对象已经构造好了,后者假设是在一段申请的raw memory里面,要先construct再进行copy。

当然对于原始类型来说,不用construct,所以其实uninitialized_copy如果遇到原始类型会调用copy,如果不是就要一个一个调用construct

这么做的原因,在上面那个连接里面有解释。

简单来说,就是如果是定义的类,有可能会有动态分配内存持有指针的情况,如果没有调用构造函数,而是直接使用,

如果直接使用,那么指针未经初始化,delete一个未经初始化的指针,后果很严重。

因为未经初始化的指针,指向一个不确定的内存空间,这个内存空间可能正在被使用,存放重要信息,

这个时候你把这个内存里面的内容delete=destroy(调用析构函数)+deallocate(将内存返还给系统)

只能说,雪崩。

转载地址:http://rniei.baihongyu.com/

你可能感兴趣的文章
从零开始学Hadoop----浅析HDFS(二)
查看>>
从零开始学Hadoop----浅析HDFS(三)
查看>>
从零开始学Hadoop——浅析MapReduce(一)
查看>>
从零开始学Hadoop——浅析MapReduce(二)
查看>>
NoSql之初识HBase
查看>>
用索引来实现幂等
查看>>
大数据的仓库Hive学习(一)
查看>>
大数据的仓库Hive原理(二)
查看>>
大数据的仓库Hive原理(三)
查看>>
MyBatis的优化注意点
查看>>
String.format参加字符串拼接大比拼
查看>>
如何使用才能让缓存更高效
查看>>
MySQL提升效率之limit
查看>>
死锁剖析
查看>>
抽丝剥茧Reactor模式
查看>>
多线程——同步-异步-阻塞-非阻塞
查看>>
多线程——临界区-锁
查看>>
多线程——java线程池简介
查看>>
多线程——Java线程池原理深入
查看>>
多线程——并发锁的集结号
查看>>