Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/148.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 在C++;,如何通过给定对象的成员来查找对象向量中的某些项?_C++_Object_Vector - Fatal编程技术网

C++ 在C++;,如何通过给定对象的成员来查找对象向量中的某些项?

C++ 在C++;,如何通过给定对象的成员来查找对象向量中的某些项?,c++,object,vector,C++,Object,Vector,例如,我定义了类foo和向量vec: #include <iostream> #include <vector> #include <algorithm> using namespace std; class foo { public: foo(int flag, char ch):flag(flag), ch(ch) {} int flag; char ch; }; int main(void) { vector<foo

例如,我定义了类foo和向量vec:

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
class foo {
public:
    foo(int flag, char ch):flag(flag), ch(ch) {}
    int flag;
    char ch;
};
int main(void)
{
    vector<foo> vec;
    vec.push_back(foo(1,'a'));
    vec.push_back(foo(2,'b'));
    vec.push_back(foo(3,'c'));
    //blabla...
}
#包括
#包括
#包括

但是现在我想通过给一个字符来找到一个对象,比如说“b”。如何有效地实现此目标?

您可以使用
std::find\u if
来实现此目标:

 //c++14
 std::find_if(std::begin(vec),std::end(vec),
              [](auto&& v) { return v.ch == 'b'; })

 //c++11
 std::find_if(std::begin(vec),std::end(vec),
              [](const foo& v) { return v.ch == 'b'; })
如果您发现自己多次需要此模式,可以将其封装在函数中:

//c++14, c++11 version left as exercise
decltype(auto) find_foo (const std::vector<foo>& vec, char c)
{
    return std::find_if(std::begin(vec),std::end(vec),
                        [c](auto&& v) { return v.ch == c; });
}
//c++14、c++11版本留作练习
decltype(自动)find_foo(const std::vector&vec,char c)
{
返回std::find_if(std::begin(vec),std::end(vec),
[c] (auto&&v){return v.ch==c;});
}
更好的选择可能是使用
std::unordered_map
而不是
std::vector

intmain()
{
std::无序_图我的_图;
我的地图['a']=1;
我的地图['b']=2;
我的地图['c']=3;

cout如果向量已排序(如您的示例中所示),则可以使用对数性能的下限。如果向量未排序,则可以使用find来获得线性性能。

您可以使用标准算法
std::find\u If
在标题
中声明。例如

#include <iostream>
#include <algorithm>

class foo {
public:
    foo(int flag, char ch):flag(flag), ch(ch) {}
    int flag;
    char ch;
};

int main()
{
    std::vector<foo> vec;

    vec.push_back(foo(1,'a'));
    vec.push_back(foo(2,'b'));
    vec.push_back(foo(3,'c'));

    char ch = 'b';
    auto it = std::find_if( vec.begin(), vec.end(), 
                            [&]( const foo &f ) { return f.ch == ch; } );

    if ( it != vec.end() ) std::cout << it->flag << ' ' << it->ch << std::endl;

}    
class foo {
public:
    foo(int flag, char ch):flag(flag), ch(ch) {}
    int flag;
    char ch;
    class find_by_ch
    {
    public:        
        find_by_ch( char ch ) : ch( ch ) {}
        bool operator ()( const foo &f ) const { return f.ch == ch; }
    private:
        char ch;
    };        
};

//...

auto it = std::find_if( vec.begin(), vec.end(), foo::find_by_ch( 'b' ) );
另一种方法是将seach作为类本身的接口

#include <iostream>
#include <algorithm>

class foo {
public:
    foo(int flag, char ch):flag(flag), ch(ch) {}
    int flag;
    char ch;
};

int main()
{
    std::vector<foo> vec;

    vec.push_back(foo(1,'a'));
    vec.push_back(foo(2,'b'));
    vec.push_back(foo(3,'c'));

    char ch = 'b';
    auto it = std::find_if( vec.begin(), vec.end(), 
                            [&]( const foo &f ) { return f.ch == ch; } );

    if ( it != vec.end() ) std::cout << it->flag << ' ' << it->ch << std::endl;

}    
class foo {
public:
    foo(int flag, char ch):flag(flag), ch(ch) {}
    int flag;
    char ch;
    class find_by_ch
    {
    public:        
        find_by_ch( char ch ) : ch( ch ) {}
        bool operator ()( const foo &f ) const { return f.ch == ch; }
    private:
        char ch;
    };        
};

//...

auto it = std::find_if( vec.begin(), vec.end(), foo::find_by_ch( 'b' ) );

仅使用
char
作为参数定义
foo
的隐式构造函数

foo(char ch) : ch(ch), flag(int()) {
}
将默认参数添加到现有构造函数中

foo(char ch, int flag = int()) : ch(ch), flag(flag) {
}
重载比较运算符

bool operator ==(const char & rhs) {
    return ch == rhs;
}
然后可以直接使用
std::find

vector<foo>::iterator it = std::find(vec.begin(), vec.end(), 'b');
if (it != vec.end()) {
    ...    // do something
}
vector::iterator it=std::find(vec.begin(),vec.end(),'b');
如果(it!=vec.end()){
…做点什么
}
然后,工作代码将如下所示

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;

class foo {
public:
    foo(char ch, int flag = int()) : flag(flag), ch(ch) {}
    int flag;
    char ch;
    inline bool operator ==(const char & rhs) { return ch == rhs; }
};

int main(void) {
    vector<foo> vec;
    vec.push_back(('a', 1));
    vec.push_back(('b', 2));
    vec.push_back(('c', 3));
    vector<foo>::iterator it = find(vec.begin(), vec.end(), 'b');
    if (it != vec.end())
        cout << "found" << endl;
    return 0;
}
#包括
#包括

#包括演示。

你知道如何在向量上迭代并使用==运算符吗?你也可以使用
std::find
@DavidHaim我知道,但我觉得当向量变得太大时效率很低。所以…^你不是在寻找
std::map
?@HaroldHuang如果你想要高效的搜索,请使用排序向量和二进制搜索谢谢你的回答,但是我的编译器说第一个代码块中的
自动
是不允许的,我也不知道为什么。我使用的是Visul Studio 2012。这是一个C++14功能,只需使用
常量foo&
即可。@Harold Huang什么不清楚?另请参阅我的更新帖子。:)哦,我已经讲清楚了。那是nks一百万!后一种方法很鼓舞人心。但似乎不允许接受多个答案,对不起。我喜欢后一种方法。真的很糟糕。