不是直接的方法。
一种选择是检查地图中的每个值,直到找到您要查找的内容。显然,这将是O(n)。
为了做到这一点,您可以编写一个for()循环,或者您可以使用std::find_if()。为了使用find_if(),您需要创建一个谓词。在C++11中,这可能是一个lambda:
typedef std::map <unsigned, Student> MyMap;
MyMap myMap;
const string targetName = "Jones";
find_if (myMap.begin(), myMap.end(), [&targetName] (const MyMap::value_type& test)
{
if (test.second.mName == targetName)
return true;
});
如果您正在使用C++03,那么这可能是一个函数对象:
struct MatchName
: public std::unary_function <bool, MyMap::value_type>
{
MatchName (const std::string& target) : mTarget (target) {}
bool operator() (const MyMap::value_type& test) const
{
if (test.second.mName == mTarget)
return true;
return false;
}
private:
const std::string mTarget;
};
find_if (myMap.begin(), myMap.end(), MatchName (target));
另一种选择是构建索引。该索引可能是另一个映射,其中键是您想要查找的任何值,而值是指回主映射的某种索引。
假设您的主映射包含
Student
对象,其中包含名称和其他一些内容,并且此映射中的键是学生ID,即整数。如果您想查找具有特定姓氏的学生,则可以构建一个索引映射,其中键是姓氏(可能要在此处使用
multimap
),而值是学生ID。然后,您可以索引回主映射以获取其余
Student
属性。
第二种方法存在挑战。在添加或删除元素时,必须使主映射和索引(或指数)同步。您必须确保选择为索引中的值的索引不是可能更改的内容,例如指针。如果您正在进行多线程操作,则必须考虑如何保护映射和索引,而不会引入死锁或竞争条件。