您的位置:首页 > 其它

STL源码学习——Lists(链表)

2012-05-12 23:17 357 查看
STL源码学习——Lists(链表)

  今天突然想起来看看开源项目,找了找最后决定好好看看经典的STL喵~
  和STL里的代码比起来我突然觉得以前写的代码也太不规范了喵,估计很多ACMer都一样吧喵。

  先从简单的看、先挑了一发list的源码来看。总结如下:

    欢迎大家一起讨论喵~

  1 :list是用双向循环链表实现的,就是说 list.end()+1 == list.begin()
  2 :list中有一个关键结点,这个结点是 list.end()
  3 :在看了list中的erase函数后,发现这个函数没有对end()结点进行特殊处理,所以很遗憾list在erase(end)后就会出现一些意想不到的情况,比如以下代码会让list容器死循环喵~(虽然这个操作本来就是非法的)

list::sort()

void sort(_StrictWeakOrdering __comp)
{
// Do nothing if the list has length 0 or 1.
if (_M_node._M_data->_M_next != _M_node._M_data &&
(_M_node._M_data->_M_next)->_M_next != _M_node._M_data)
{
list<_Tp, _Alloc> __carry;
list<_Tp, _Alloc> __counter[64];
int __fill = 0;
while (!empty())
{
__carry.splice(__carry.begin(), *this, begin());   //个位加一
int __i = 0;
while(__i < __fill && !__counter[__i].empty())
{
__counter[__i].merge(__carry, __comp);
__carry.swap(__counter[__i++]);
}
__carry.swap(__counter[__i]);
if (__i == __fill) ++__fill;
}

for (int __i = 1; __i < __fill; ++__i)
__counter[__i].merge(__counter[__i-1], __comp);
swap(__counter[__fill-1]);
}
}


  7 :关于resize()我以前一直以为list会存放一个size_val,结果它木有存,resize的复杂度是线性的。所以如果size比较大的话,还是少resize()为好喵。

当然现在也可以理解为什么没有存放size_val了喵,因为存在这个时间复杂度为O(1)的insert函数。

  void insert( iterator pos, input_iterator start, input_iterator end );


  

  8 :“operator=” list里这个函数比我想像的要聪明喵。
  我以为它会先erase(begin(), end()),然后再一个一个的加进去。
  结果它是先将就目标list中已创建的结点先用着,然后采用”多退少补“的原则喵~
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: