set 是不是可以将 std::vector 作为底层存储来存储其元素?
Posted
技术标签:
【中文标题】set 是不是可以将 std::vector 作为底层存储来存储其元素?【英文标题】:is it possible for set to have std::vector as underlying storage for storage of its elements?set 是否可以将 std::vector 作为底层存储来存储其元素? 【发布时间】:2010-09-24 17:53:49 【问题描述】:对于小型集合,无论应用什么操作,std::vector 几乎肯定是最好的容器。是否可以将 std::vector 作为元素集容器的底层存储,而不是涉及大量堆分配的红黑树(也许 boost 有什么?)还是我必须自己发明它?
由于性能原因,普通 std::vector 和 std::sort 不是一个选项,并且 std::inplace_merge 容易出现编码错误(迭代器无效等)。
编辑:澄清问题
【问题讨论】:
同意 -1 - 你的 q 可能更清楚。示例代码? 他的问题对我来说很有意义。他似乎在问是否可以指示 std::set 维护一个排序的向量作为其内部存储,而不是它通常使用的红/黑树。 @Tyler - 我同意这很有可能 【参考方案1】:无法指定 STL 集的底层结构。充其量你可以编写一个分配器,它使用一个向量来提供 set 使用的内存,这可能是你想要的,也可能不是你想要的。
【讨论】:
【参考方案2】:对于小尺寸,所有容器都非常高效;除非您知道自己有性能问题,否则只需使用 set
你的情况
使用向量交易功能(排序、唯一性)来获取存储大小
使用 set 则相反
如果您需要排序和唯一性,那么请选择具有该功能的容器,除非您确定这是一笔糟糕的交易
【讨论】:
有趣 - 前 2 个答案给出了相反的建议 :-) 使用 std::set 存储 10 个整数是一种过度杀伤力,因为 IIRC,默认分配器将调用 operator new 并且每次分配至少花费数百个处理器周期。使用 std::vector 可以将成本降低一个数量级 所以在现代处理器上,它将花费 500(比方说)* 10 = 5000 个周期。即5-10微秒;证明我的观点。【参考方案3】:如果你的意思是你可以拥有
std::set<std::vector<MyType> > myIdealContainer;
那么答案是肯定的,只要您能够将向量有意义地包装在使其可排序的东西中(因此 set 可以对其成员进行排序)。但请注意复制效率低下。
如果你的意思是我可以用向量实例化集合作为自定义分配器的存储,那么我不知道你会怎么做(或者你为什么想要)。
如果你的意思是你能像对待集合一样对待向量,那么答案是否定的。如果您的数据集很小并且匹配容器成员的成本很低,请使用向量,保留插入的顺序并使用 std::find 线性扫描匹配项。如果数据集很大和/或匹配成本很高,请使用 set。
【讨论】:
【参考方案4】:我想你在找boost::container::flat_set
flat_set 与 std::set 类似,但它的实现方式类似于有序向量。
【讨论】:
【参考方案5】:不,不能指定用于std::set
的容器,您只能使用std::queue
或std::stack
等容器适配器来执行此操作。 std::set
是具有自身性能要求的基本容器之一。 std::vector
可能不是所有情况下的最佳容器。例如,如果您想要一个良好的查找性能,您会选择 set,因为 find
是 O(log n)
,而对于向量,它是 O(n)
【讨论】:
有问题的馆藏很小。因此 std::set 是不可行的,因为隐藏在 O(1) 中的高常数用于插入。【参考方案6】:也许我误解了你,但如果你试图使用一个 std::set ,它有一个 std::vector 用于数据存储(所以集合的所有数据实际上都存储在向量中),那么答案应该是“不”。 原因很简单,c++ std::set 实现是一个二叉搜索树,而 std::vector 只管理一个简单的数组/内存块。
【讨论】:
以上是关于set 是不是可以将 std::vector 作为底层存储来存储其元素?的主要内容,如果未能解决你的问题,请参考以下文章
将 std::vector 作为 numpy 数组返回给 python
将元素从 std::vector 复制到 std::stack c++