MyLib 之 数组

Array表示分配后不可更改的数组。

Vector表示分配后可以更改的数组,具体起什么名字以后再说吧。

vector采用了连续内存空间的布局,

start指向首元素所在的位置

finish指向最后一个有效元素所在的后一个位置,这样在新增元素的时候直接就可以放在finish所指的位置,然后再将finish自增即可。

end指向最后一个可用空间的后一个位置。遵循左闭右开。

template<typename _Tp, typename _Alloc>
class vector
{
private:
    _Tp* _start;
    _Tp* _finish;
    _Tp* _end;
}

vector的底层通过malloc分配空间(或者也可能是operator new)。众所周知,malloc函数是不会调用类的构造函数的。如果我传递进去的模板参数是一个类类型,这样岂不是出大问题了。

其实不然,STL直接将空间分配与元素构造分离开来。对于内置类型,无需进行构造的调用一个方法,需要进行构造的类型调用另一个方法,这样提高了效率。

添加元素整体分为两种情况:空间充足与空间不充足。

如果空间足够,自然就很好解决了,直接将这些元素填充到后面的空间中,再改变finish的指向即可。

如果空间不够,这就要涉及到vector空间自增长的奥秘了。其实原理非常的简单,重新申请一块新空间,将原空间的数据copy进新空间,添加数据,销毁原空间。做法其实和array空间不够时一样,只是vector将其封装好了之后就不需要我们操心这么多了。当然,空间的增长也是需要一定的技巧的。不然我每次空间不够,都只申请比原空间大1的空间,这样反复的申请释放极大的浪费效率,不值当。在vector中,每次的自增长都会是原空间的两倍,甚至更多。

在进行插入操作的时候整体分为两种情况,空间充足和空间不充足的情况。空间足够的时候又分为两种。插入的元素需要进行构造和不需要进行构造的情况。

上面提到过,STL中空间的分配和元素的构造是分离开来的,当空间充足时,插入时,先将后面的数据移动到更后面,然后插入即可。(插入多个的时候略有不同)。直接填充,并没有构造,此时并没有调用需要进行构造的函数(uninitialized系列)可以看到,是否进行构造针对的是地址空间,而不是元素的值。当然,对于push_back()这个函数来说,它永远只可能出现空间不足或者填充的元素需要进行构造的情况。

 

 

 

 

 

 

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值