C++中set的插入和查找 与二分查找对比 效率如何

作者&投稿:厍民 (若有异议请与网页底部的电邮联系)
c++ 中 set数据结构和hashset数据结构的查询效率~

在STL中,set是以红黑树(RB-tree)作为底层数据结构的,hash_set是以Hash table(哈希表)作为底层数据结构的。set可以在时间复杂度为O(logN)情况下插入、删除和查找数据。hash_set操作的时间复杂度则比较复杂,这取决于哈希函数和哈希表的负载情况。
一般来说,查询的数据量越大,hash_set的性能优势越明显。

//在a中寻找num的下标,没有找到返回-1。int findIndex(int num,int a[],int size){ return bs(num,a,0,size-1);}int bs(int num,int a[],int begin,int end){ if(endnum)return bs(n,a,begin,mid-1); return bs(n,a,mid+1,end);}

Set的底层是用的红黑树。而数组就是顺序表。这两种数据结构优劣不同。
如果已知数据有序,那么顺序表的二分查找当然最快。但是顺序表的插入性能极差,比如我要在头部插入一个数据,则要吧所有的数据后移一格,开销极大。红黑树则平衡了插入性能和查找性能。所以就有你看到的数据了,set的时间空间性能都比较差。
顺序复制数组,不涉及到插入,所以数组很快。但是插入,删除的话,红黑树需要一些时间来调整结构,所以有时间和空间的开销。
如果你有这样的一批数据,数量比较大,假设25w左右,他们需要频繁的发生插入,删除,以及查找工作,那么数组就无法处理了,红黑树则是更好的选择。
你可以研究一下红黑树的性质,就很容易理解了。

如果有不清楚的地方请追问。

set不是二分查找是红黑树。既然是树空间消耗大很好解释...

复杂度的确都是logN(排序其实是平均logN,最坏情况下是logN^2),有一个小问题是二分查找是绝对的2的对数次循环,红黑树并不是绝对平衡的平均下来会比2的对数次循环多。不过这个只是小问题。另外一个小问题是红黑树的每次循环的代价要比排序大,排序只是一个比较和一个可能的交换,红黑树是一个申请内存,初始化结构加一个可能的涉及三个节点的旋转。
然后真正影响速度的大问题是内存局域性(memory locality),内存局域性差就不能有效利用CPU的高速缓存。
排序方法你写入的时候不读取数据,排序的时候用的快速排序算法某种意义上也是一个牺牲绝对复杂度(最坏的情况下是logN^2)从而提高内存局域性的算法。二分查找是一个内存局域性差的操作,但是你只执行了一次。
而set每次插入都是内存局域性几乎等于没有的操作,而且set本身的数据量又大很多,所以自然就慢了。

set更适合需要不断插入,并且随时要在里面查找的情况(这种情况一般叫在线排序online sorting)。set插入的复杂度是logN,而排序的方法插入的复杂度是N。所以只要N足够大,就能抵消内存局域性的代价。但是你的情况显然不符合。


arraylist中add()与set()有何不同
e set(int index,e element):用指定的元素替换列表中指定位置的元素。返回值是通用的(由e决定)。有两种加法,两种方法的参数和返回值不同。boolean add(e e):将指定的元素(e)添加到此列表的末尾,并返回布尔类型。void add(int index,e element):将指定的元素(element)插入此列表中...

es6中set类型是有序的还是无序的
有序,你可以在官方的Set找到答案,Set的遍历顺序就是插入顺序。这个特性有时非常有用,比如使用 Set 保存一个回调函数列表,调用时就能保证按照添加顺序调用。

Linux中的set命令的详细解释
一、Linux中的set命令的详细解释 功能说明:设置shell。语法:set [+-abCdefhHklmnpPtuvx]补充说明:用set 命令可以设置各种shell选项或者列 出shell变量.单个选项设置常用的特性.在某些选项之后-o参数将特殊特性打开.在某些选项之后使用+o参数将关闭某些特性,不带任何参数的set命 令将显示shell的全部...

Java中Set、List、Map集合类(接口)的特点及区别是什么?
Set:检索元素效率低下,删除和插入效率高,插入和删除不会引起元素位置改变;List:和数组类似,List可以动态增长,查找元素效率高,插入删除元素效率低,因为会引起其他元素位置改变;Map:适合储存键值对的数据。Java是一门面向对象编程语言,不仅吸收了C++语言的各种优点,还摒弃了C++里难以理解的多继承、...

Set集合,放的元素不能重复,请问它的判断重不重复是怎么实现的?
你好,首先要明白一点:加入Set里面的元素必须定义equals()方法以确保对象的唯一性。第一个问题:TreeSet的底层实现是采用红-黑树的数据结构,采用这种结构可以从Set中获取有序的序列,但是前提条件是:元素必须实现Comparable接口,该接口中只用一个方法,就是compareTo()方法。当往Set中插入一个新的元素...

java中list和set接口 set不可以重复,list可以重复
这就是他们的设计原则,至于你说的判断机理其实也是可以用这个解释的,用途不同就有了区分 他们判断新元素和已有元素的hashcode是否相等:1. 不相等则认定不重复,可以插入;2 相等则再调用元素的equals()方法,跟已有元素比较 (1)若不相等,则认定不重复,可以插入;(2)若相等,则认定重复,不插入...

flutter Set集合妙用
从源码我们可知,Set()是一个工厂构造方法,根据工厂构造方法的特点,Set是由LinkedHashSet实例化的。从上面注释可知,HashSet是无序的,LinkedHashSet保持着子元素插入的顺序。而Set是由LinkedHashSet实例化的,所以Set保持着子元素插入的顺序。 如想要深入分析LinkedHashSet,LinkedHashSet源码中有很多...

PLC中RST和SET的区别?
2、SET:SET指令可用于Y,M和S。三、特点不同 1、RST:RST指令可将数据寄存器D、变址寄存器Z租V的内容清零,RST指令还用来复位积算定时器T246~T255和计数器。2、SET:功能与数字电路中R–S触发器的功能相似,SET指令之间可以插入别的程序。如果指令之间没有别的程序,最后的指令有效。参考资料来源...

matlab中的set命令怎么用啊
为一句柄的向量。在这种情形下,命令set 可以设置所有对象的属性值。set(H,a) 用指定的属性值设置由H 标志的对象的属性。其中a 为一结构数组,该 结构数组的域名为对象的属性名,域名值为相应属性名的属性值。set(H,pn,pv…) 对由H 指定的所有对象中指定的细胞数组属性名pn 设置为相应 的细胞...

hashset是无序的,list是有序的,请问这句话是什么意思,怎么理解
List,Set都是继承自Collection接口。List特点:元素有放入顺序,元素可重复 。Set特点:元素无放入顺序,元素不可重复。注意,元素虽然无放入顺序,但是元素在set中的位置是有该元素的HashCode决定的,其位置其实是固定的。有序或无序是指是否按照其添加的顺序来存储对象。List 是按照元素的添加顺序来存储的...

共和县13261054241: C++中set的插入和查找 与二分查找对比 效率如何 -
督栋复方: Set的底层是用的红黑树.而数组就是顺序表.这两种数据结构优劣不同. 如果已知数据有序,那么顺序表的二分查找当然最快.但是顺序表的插入性能极差,比如我要在头部插入一个数据,则要吧所有的数据后移一格,开销极大.红黑树则平衡了插入性能和查找性能.所以就有你看到的数据了,set的时间空间性能都比较差. 顺序复制数组,不涉及到插入,所以数组很快.但是插入,删除的话,红黑树需要一些时间来调整结构,所以有时间和空间的开销. 如果你有这样的一批数据,数量比较大,假设25w左右,他们需要频繁的发生插入,删除,以及查找工作,那么数组就无法处理了,红黑树则是更好的选择. 你可以研究一下红黑树的性质,就很容易理解了.如果有不清楚的地方请追问.

共和县13261054241: c++的stl的priorityqueue中如何做二分查找? -
督栋复方: 答: 无法做. 二分需要有序, priorityqueue不是有序的概念.

共和县13261054241: 在C++中set与multiset的区别 -
督栋复方: 我看这个帖子能很好的回答你的问题:http://apps.hi.baidu.com/share/detail/17392185 以下是它的部分内容 C++ STL set和multiset的使用1,set的含义是集合,它是一个有序的容器,里面的元素都是排序好的,支持插入,删除,查找等操作,就 像...

共和县13261054241: C++容器"set"中.second的意义 -
督栋复方: set的带有一个键参数的insert版本函数返回pair类型对象,该对象包含一个迭代器和一个bool值,迭代器指向拥有该键的元素,而bool值表明是否添加了元素.这里的second即是返回的pair里的bool值.

共和县13261054241: C++ 的 set 集合应该怎么用,求简单的初始化,添加值,和遍历!!! -
督栋复方: #include <iostream> #include <set> using namespace std; void main() {set<int> s1; //空set集合set<int>::iterator it; int a[]= {1,2,3,4,5};set<int> s2 (a,a+5); //利用指针对象初始化set集合s2.insert(0); //插入方法1s2.insert(s2.begin(),7); //插...

共和县13261054241: 在c++中,怎么将vector中的元素插入到set中 -
督栋复方: stl算法中有个copy函数可以实现从vector中插入set中. 具体实现如下:#include #include #include int main() {std::set input;input.insert(5);input.insert(6); std::vector output;std::copy(input.begin(), input.end(), output.begin());return ...

共和县13261054241: 关于C++中的2分搜索算法 请教高手
督栋复方: 这个是利用STL的算法来实现的:#include #include #include using namespace std; template pair BinarySearch(T *beg, T *end, T val) { return make_pair(lower_bound(beg, end, val), upper_bound(beg, end, val)); } int main() { int a[] = {1,1,1,2,2,2,3,3...

共和县13261054241: c++ stl set 中find方法是如何实现的 -
督栋复方: 是用在平衡二叉树上查找的算法实现的,复杂度是O(log n).STLport里面的实现代码如下: _Base_ptr _M_find(const _KT& __k) const { _Base_ptr __y = __CONST_CAST(_Base_ptr, &this->_M_header._M_data); // Last node which is not less ...

共和县13261054241: C++中,如何往集合(set)里插入元素?最后一句有错误,请大家帮忙改正 -
督栋复方: set插入元素直接不能使用back_inserter.set_union(A.begin (),A.end (),B.begin (),B.end (),inserter(C, C.begin()));

共和县13261054241: 有关C++二分查找 -
督栋复方: C 和C++的/是除法取整.比如你这里的11个元素,11/2按照自然结果为5.5,但是在C和C++中整数进行相除,仍然得到整数结果,所以就是5.5的整数部分即5.至于是第五个还是第六个元素,要看你这个5是作为数组的下标索引,还是用于其它的计算元素的顺序了.(按照通常的做法,是作为下标索引,就是第六个元素)

本站内容来自于网友发表,不代表本站立场,仅表示其个人看法,不对其真实性、正确性、有效性作任何的担保
相关事宜请发邮件给我们
© 星空见康网