美文网首页
Effective STL 第34条

Effective STL 第34条

作者: 懒生活 | 来源:发表于2022-10-12 20:57 被阅读0次

为什么有些算法需要排序的区间

binary_search算法是二分查找, 这种查找需要查找空间的序列是有序的. 为了二分查找的效率,给binary_serach指定的区间,最好用"随机访问迭代器"指定. 因为binary_search运行过程常常需要直接取中间值. 如果迭代器支持随机访问,那么通过中间下标可以快速的访问.但如果迭代器不支持这种快速的随机访问,那binary_search只能通过迭代器自增加或减少一点点的挪动,那样的效率就会很低.
lower_bound(first, last, val) 从区间中找到不小于val值的 (大于或者等于)
upper_bound(first, last,val) 从区间中找到大于val值的元素
pair<int*, int*> range = equal_range(a, a + 9, 4); equal_range从区间找到等于val的起始位置和结束位置.
这四个查找都是基于二分法.所以要求区间是排序的区间.

求集合的算法为什么要求是排好序的区间

4个求集合的算法,分别是求并集set_union, 求交集set_intersection, 求差集set_difference, 求对称差集set_symmetric_differnce.
只有了解这四个算法的实现你才能知道为什么他们需要排序空间。

求并集

最笨的做法,取出集合一的元素,然后遍历集合2一下,如果元素也在集合2上,则放入并集。这样的操作对集合一的元素要来一遍,对集合2的元素也要来一遍。复杂度是2(集合1个数)(集合2个数)。
stl的set_union算法是这样的
对于队列s1,s2, 分别从头开始遍历,走一格判断一下:

  • 如果两个元素相同,取s1的元素,取出元素的队列向前一格。
  • 如果两个元素不同,取小的元素,并向前一格
  • 如果有一个集合已经到达尾端,取出另一个集合的所有剩余元素

求交集

set_intersection

  • 如果两个元素相同,取s1元素,并向前一格
  • 如果两个元素不同,s2一直向前
  • 任何一个集合到达尾端,停止操作

求差集

set_difference
注意这个算法的目的是求出s1上有,s2上没有的集合。

  • 如果两个元素相同,都向前一格
  • 如果s1的元素大于s2, s2一直向前
  • 如果s1的元素小于s2, 取出s1元素
  • 如果s2已经到末端,s1的剩余元素取出。

求对称差集

  • 如果两个元素相同,都向前一格
  • 如果两个元素不同,取小元素,小元素的队列向前一格
  • 如果有集合到达尾端,剩余的全部取出。

merge算法

merge算法和set_union的算法很类似,不过有一点微小的区别。
merge最后得到的元素个数一定是两个集合的总和,是两个集合没有损失的合集,并且合集也保持排序性。
但是set_union相同的一对只会取一个保留。具体的做法需要熟悉set_union的算法

inplace_merge算法

这个算法也要求指定的区间段是排过序的。他的目的是用于这种场景。一个容器有两段,【first middle) 【middle last)这两段本身是排序的,【first, last)不满足排序。inplace_merge的目的是把这两段融合,位置还是这个队列,不过实现了完整的排序。

includes算法

目的是判断s1是否涵盖s2
他使用的算法应该类似set_intersection. 也是要求排序的区间。

unique

unique是去重的,但是要注意的是他只能对付连续的重复。所以对于不连续的重复如果也要去除的话,需要先排序一下。

unique_copy

unique_copy 类似unique。 好处是他对原队列是不会影响的。他只会把不重复的数据copy到另一个容器。

相关文章

  • EFFECTIVE+STL中文版:50条有效使用STL的经验

    《Effective STL中文版:50条有效使用STL的经验》是EffectiveC++的第3卷,被评为“值得所...

  • 常用的 STL 查找算法

    常用的 STL 查找算法 《effective STL》中有句忠告,尽量用算法替代手写循环;查找少不了循环遍历,在...

  • Effective STL 第7条

    容器中的对象如果是指针,指针指向的资源,容器没有办法自动释放. 问题引出 容器在自己析构的时候,会把包含的对象逐个...

  • Effective STL 第28条

    正确使用reverse_iterator对于任何一个容器, 使用iterator, 你只可能正向正序访问容器内部的...

  • Effective STL 第22条

    主要不要修改set mutipleSet的key

  • Effective STL 第30条

    如果是区间操作,注意确保容器具有足够的区间 这个很矛盾, 我们害怕使用数组,就是因为数组有可能越界.为了不去考虑数...

  • Effective STL 第31条

    准确的选择排序算法 如果要对一个数列进行完全的排序,那么用sort是个不错的选择.但是如果只是部分排序, 要考虑更...

  • Effective STL 第34条

    为什么有些算法需要排序的区间 binary_search算法是二分查找, 这种查找需要查找空间的序列是有序的. 为...

  • Effective STL 第19条

    理解相等于等价相等的基础是 == , 如果x==y成立,就说明x和y的值相等对于有顺序关系的容器, 为了顺序的存在...

  • Effective STL 第25条

    散列表: 用key可以作为索引快速找到对应的value. 且这些对象在容器里面不排序. 散列表和标准关联容器set...

网友评论

      本文标题:Effective STL 第34条

      本文链接:https://www.haomeiwen.com/subject/kokxzrtx.html