STL中的Binary_search设置了set的成员函数find?

Abh*_*hek 6 c++ stl c++11

为什么我们有两种方法来搜索集合中的元素?

另外,find算法可用于查找列表或向量中的元素,但是这些提供成员函数以及成员函数的危害会比通用算法更快吗?

为什么我们需要删除算法并创建关于擦除的所有戏剧删除其中删除只会移动元素然后使用擦除删除实际元素.就像STL列表提供成员函数删除为什么其他容器只能提供删除功能和完成它?

Ali*_*Ali 8

STL中的Binary_search设置了set的成员函数find?
为什么我们有两种方法来搜索集合中的元素?

二进制搜索返回boolset::find()和迭代器.为了比较苹果和苹果的算法来比较set::find()与IS std::lower_bound()也返回迭代器.

您可以应用由一对(正向/双向/随机访问)迭代器指定std::lower_bound()的任意排序范围,而不仅仅是在a上std::set.所以std::lower_bound()有理由.由于std::set正好是一个排序的范围内,你可以调用

std::lower_bound(mySet.begin(), mySet.end(), value);
Run Code Online (Sandbox Code Playgroud)

但是

mySet.find(value);
Run Code Online (Sandbox Code Playgroud)

呼叫不仅更简洁,而且效率更高.如果你查看实现,std::lower_bound()你会发现一些std::advance(__middle, __half);具有不同复杂性的东西,具体取决于迭代器(无论是前向/双向/随机访问迭代器).在这种情况下std::set,迭代器是双向的并且推进它们具有线性复杂性,哎哟!与此相反,std::set::find()保证执行在数时间复杂度搜索.底层实现(在libstdc ++的情况下是红色和黑色树)使它成为可能.set::find()也有道理,因为它比调用更有效std::lower_bound()std::set.

另外,find算法可用于查找列表或向量中的元素,但是这些提供成员函数以及成员函数的危害会比通用算法更快吗?

我不知道如何为列表或向量提供更快的成员函数,除非容器已排序(或拥有一些特殊属性).

为什么我们需要删除算法并创建关于擦除的所有戏剧删除其中删除只会移动元素然后使用擦除删除实际元素.就像STL列表提供成员函数删除为什么其他容器只能提供删除功能和完成它?

我可以想到两个原因.

是的,STL严重缺乏许多便利功能.在整个容器上使用算法时,我常常觉得自己生活在一个开始的地狱之中; 我经常证明我自己的包装器接受一个容器,例如:

template <typename T>
bool contains(const std::vector<T>& v, const T& elem) {

    return std::find(v.begin(), v.end(), elem) != v.end();
}
Run Code Online (Sandbox Code Playgroud)

这样我就可以写了

if (contains(myVector, 42)) { 
Run Code Online (Sandbox Code Playgroud)

代替

if (std::find(myVector.begin(), myVector.end(), 42) != myVector.end()) { 
Run Code Online (Sandbox Code Playgroud)

不幸的是,你经常需要自己动手或使用助推器.为什么?因为标准化是痛苦而缓慢的,所以标准化委员会关注更重要的事情.委员会的人经常捐出空闲时间,而不是为工作付钱.

现在从向量中删除元素可能很棘手:您是否关心元素的顺序?你的元素是POD吗?您的异常安全要求是什么?

假设您不关心元素的顺序,并且您想要删除第i个元素:

std::swap(myVector[i], myVector.back());
myVector.pop_back();
Run Code Online (Sandbox Code Playgroud)

甚至更简单:

myVector[i] = myVector.back(); // but if operator= throws during copying you might be in trouble
myVector.pop_back();
Run Code Online (Sandbox Code Playgroud)

在带有移动语义的C++ 11中:

myVector[i] = std::move(myVector.back());
myVector.pop_back();
Run Code Online (Sandbox Code Playgroud)

请注意,这些是O(1)操作而不是O(N).这些是标准委员会向您提出的效率和异常安全考虑因素的示例.提供成员函数和"一刀切"并不是C++方式.

说完这些之后,我再说一遍,我希望我们有更多的便利功能; 我理解你的问题.