stl源码剖析带目录_侯捷《STL源码剖析》 | 容器详解 Deque

Deque

Deque为双端队列,提供双端进出的操作,特点如下:

  • 包含一个map链表,用来将存放元素的多个缓冲区“连接”起来,使用者使用时像是拥有了连续空间。
  • 包含start、finish两个迭代器和一个pointer指针

13bf880399b272f75cda9c5269d70eb4.png

Deque的实现:

df3b647fd757e598dfedcc6f6f1240dd.png

Deque的iterator

deque迭代器的设计比较精巧,包含node、first、last、cur四个指针。特定如下:

  • 若_Duque_iterator中node指向某个缓冲区,first指向buffer开端,last指向buffer末端,cur指向buffer存元素的位置。
  • 对于start迭代器,其cur指向buffer存元素的开头;对于end迭代器,其cur指向buffer存元素的末尾。
  • 用于遍历的iterator的cur指向buffer中的当前访问元素,当iterator走到buffer边界时,要有能力跳到下一个buffer,通过map中的node实现。

d1f2ca7694f3f9d21698e448df9118cb.png

insert操作

开头插入调用push_front();末尾调用push_back();中间调用insert_aux();

8922cd341426cbdbfa4c3da8a361c310.png

insert操作会计算插入位置position到首尾的距离,在尽量减少元素移动的情况下加入。

612ec4e5fd65f44347db872c582101f0.png

deque操作符的重载

  • 操作符 [ ]
reference operator[](size_type n){
	return start[difference_type(n)];
}
  • 操作符 *
reference operator*() const{
	return *cur;
}
  • 操作符 ->
pointer operator->() const{
	return &(operator*());
}
  • 操作符 - 两对象之间的相减,a - b获得从b到a的长度。
difference_type operator-(const self& x) const{
	return difference_type(buffer_size()) * (node - x.node - 1) +
	  (cur - first) + (x.last - x.cur);
// 其中 (node - x.node - 1) 计算两根迭代器之间完整buffer的长度
// (cur - first) 计算末尾buffer的元素量
// (x.last - x.cur) 计算起始buffer的元素量
  • 操作符++、--
self& operator++(){ // 前置++
	++cur; // 切换至下一元素
	if (cur == last){ // 如果抵达缓冲区尾部
		set_node(node + 1); // 跳至下一个节点
		cur = first; // 的起点
	}
	return *this;
}

self operator++(int){ // 后置++
	self tmp = *this;
	++*this;
	return tmp; //返回当前值,但是指针已经后移
}

self& operator--(){
	if (cur == first){ // 先判断当前是否在缓冲区起点
		set_nde(node - 1);
		cur = last;
	}
	--cur;
	return *this;
}

self operator--(int){
	self *tmp = *this;
	--*this;
	return tmp;
}

// 用于跳转节点的代码
void set_node(map_pointer new_node){
	node = new_node;
	first = *new_node;
	last = first + difference_type(buffer_size());
value_type和difference_type之间的加减
  • 操作符 +和+= 用作value_type和difference_type之间的相加。
    操作符+实际调用操作符+=,+=设计时要考虑到节点可能跳过多个缓冲区。

3d2cd7387c092618ba2d6d17b74e8469.png
  • 操作符 -和-= 用作value_type和difference_type之间的相减。
    操作符-实际调用操作符-=,操作符-=可调用操作符+=。
  • 操作符[]

对象后接取址符[difference_type n],也可以用作元素的跳转。

使用容器Deque实现queue和stack

相当于一种适配器模式。

6969cb86ff32abdbe9894d1b30fa2c04.png

ab8aba4436e1877c3efc169e6378552d.png
  • stack和queue都允许遍历
  • stack和queue都可以选择list或者deque作为底层结构

dafcef7758efa688a1aa90cd4941404c.png

reference

  • 侯捷《STL源码剖析》

更多精彩文章,欢迎关注公众号“Li的白日呓语”。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值