2009-10-27 63 views
4

今天我写了一个小谓词来查找容器中的匹配符号。STL算法和const_iterators

但是我遇到了一个问题:我想在一个类的const方法内调用std::find_if这个谓词,在这个类的成员容器中搜索。

但我只注意到std::findstd::find_if都不能在const_iterators上运行!

我检查了一些C++参考,似乎没有版本std::findstd::find_if接受/返回const_iterators。我只是不明白为什么,因为从我看到的情况来看,这些算法不可能修改迭代器引用的对象。

这里是如何在SGI实现记录std::find

返回第一个迭代我在 范围[第一,最后),使得*我== 值。如果不存在迭代器,则返回last。

+0

你得到的实际错误是什么?你还可以发布一些示例代码?谢谢 – 2009-10-27 17:56:28

+2

其实,你只是误读了文档,请参阅下面的Pavel的答案。如果你测试你会发现它确实有效。 – 2009-10-27 18:09:36

+0

你的问题意味着你有一些不起作用的代码 - 特别是“但我面临一个问题” - 而实际上你只是在大声思考。如果你尝试过,你会看到它的工作,我就低估了这个问题。 – 2009-10-27 18:23:00

回答

13

std::findstd::find_if可以*::const_iterator对于给定的容器一定操作。你偶然看到这些功能的签名,并误解它们吗?

template <class InputIterator, class Type> 
InputIterator find(InputIterator first, InputIterator last, const Type& val); 

注意InputIterator这里只是一个模板类型参数的名称,以及任何const_iterator将满足它的要求。

或者,您可能会将const_iterator(即引用常量值的迭代器)与const迭代器(即本身为const的迭代器)混淆?

+0

Ohw,猜测它太晚了,我只是走了几十个文件,每次我读了我想要的,而不是写了什么x( 感谢您的耐心等待。 – NewbiZ 2009-10-27 18:15:51

5

std::findstd::find_if都采取迭代器类型为模板参数,所以他们肯定可以const_iterators操作。只是一个简单的例子:

#include <vector> 
#include <algorithm> 
#include <iostream> 
int main() { 
    std::vector<int> x; 

    std::fill_n(std::back_inserter(x), 20, 2); 
    x.push_back(3); 

    std::vector<int>::const_iterator b = x.begin(); 
    std::vector<int>::const_iterator e = x.end(); 

    std::vector<int>::const_iterator p = std::find(b, e, 3); 

    std::cout << *p << " found at position: " << std::distance(b, p) << "\n"; 
    return 0; 
} 

这应该由任何正常的C++编译器所接受,并产生类似的结果:

3中所在的位置:20

1

我刚刚有同样的问题。我有一个成员函数在成员矢量上调用find_if,编译器给我一个错误,当我尝试使成员函数const。原来,这是因为我将find_if的返回值分配给iterator而不是const_iterator。导致编译器假定参数find_if也必须是iterator而不是const_iterator,它不能从const成员向量中获得。

0

万一你在这里出于同样的原因是我:

error: no matching function for call to ‘find(std::vector<int>::const_iterator, std::vector<int>::const_iterator, int)’ 

它没有任何与const_iterator秒。你可能只是忘了#include <algorithm> :-)

0

我只是有这个代码的问题:

std::string str; 
std::string::const_iterator start = str.begin(); 
std::string::const_iterator match = std::find(start, str.end(), 'x'); 

错误是“没有匹配的过载的std ::找到”。

我需要的修复是使用cend()。令人困惑的是,不需要cbegin(),我不知道为什么该转换可以(隐式),而不是end()作为函数参数。