std 映射查找始终为真
std map find is always true
我在使用 std::map 时遇到问题,特别是在使用查找时。
我有以下代码。
class MyClass
{
update(const QVariant&);
QVariant m_itemInfo;
std::map<QVariant, int> m_testMap;
}
void update(const QVariant& itemInfo)
{
if(m_itemInfo != itemInfo)
{
// The items are not equal
m_itemInfo = itemInfo;
}
if(m_testMap.find(itemInfo) == m_testMap.end())
{
// TestMap doesnt contain key itemInfo.
m_testMap.insert(std::make_pair(itemInfo, 1));
}
// More code
}
函数 update
在我的代码中被多次调用(使用不同的 itemInfo 对象)。现在当我开始调试它时,我看到第一次调用 update
时,第一个和第二个 if 循环都进入了。到目前为止,一切都很好。但是第二次调用 update
我确实看到调用了第一个 if 循环,但跳过了第二个!我在这里错过了什么?
我猜问题是您传递给 Update 方法的第一个和第二个 QVariant
具有不同的类型(例如,bool
和 uint
)。 std::map::find
不使用 !=operator 来比较键,它默认使用 operator < (less)。如果两个比较的 QVariant
值具有不同的类型,运算符 != 和 < 可能会相互矛盾。
std::map::find
按以下方式比较键:
Two keys are considered equivalent if the container's comparison object returns false reflexively (i.e., no matter the order in which the elements are passed as arguments).
即std::map::find
认为v1等于v2
if(!(v1<v2) && !(v2>v1)) { //is TRUE !!!
}
要解决您的问题,您应该为 std:map
.
定义 less 比较
class QVariantLessCompare {
bool operator()(const QVariant& v1, QVariant& v2) const {
// ==== You SHOULD IMPLEMENT appropriate comparison here!!! ====
// Implementation will depend on type of QVariant values you use
//return v1 < v2;
}
};
并这样使用QVariantCompare
:
std::map<QVariant, int, QVariantLessCompare> m_testMap;
一个更典型的解决方案是使用 QMap
,它正确地实现了大多数 QVariant
类型的比较。它不会开箱即用 userTypes()
,但这可能仍然适合您的应用程序。
由 Володин Андрей 提出的解决方案的更简洁版本可能如下所示:
struct QVariantLessCompare {
bool operator()(const QVariant& v1,const QVariant& v2) const
{
return v1.toInt() < v2.toInt();
}
};
我在使用 std::map 时遇到问题,特别是在使用查找时。 我有以下代码。
class MyClass
{
update(const QVariant&);
QVariant m_itemInfo;
std::map<QVariant, int> m_testMap;
}
void update(const QVariant& itemInfo)
{
if(m_itemInfo != itemInfo)
{
// The items are not equal
m_itemInfo = itemInfo;
}
if(m_testMap.find(itemInfo) == m_testMap.end())
{
// TestMap doesnt contain key itemInfo.
m_testMap.insert(std::make_pair(itemInfo, 1));
}
// More code
}
函数 update
在我的代码中被多次调用(使用不同的 itemInfo 对象)。现在当我开始调试它时,我看到第一次调用 update
时,第一个和第二个 if 循环都进入了。到目前为止,一切都很好。但是第二次调用 update
我确实看到调用了第一个 if 循环,但跳过了第二个!我在这里错过了什么?
我猜问题是您传递给 Update 方法的第一个和第二个 QVariant
具有不同的类型(例如,bool
和 uint
)。 std::map::find
不使用 !=operator 来比较键,它默认使用 operator < (less)。如果两个比较的 QVariant
值具有不同的类型,运算符 != 和 < 可能会相互矛盾。
std::map::find
按以下方式比较键:
Two keys are considered equivalent if the container's comparison object returns false reflexively (i.e., no matter the order in which the elements are passed as arguments).
即std::map::find
认为v1等于v2
if(!(v1<v2) && !(v2>v1)) { //is TRUE !!!
}
要解决您的问题,您应该为 std:map
.
class QVariantLessCompare {
bool operator()(const QVariant& v1, QVariant& v2) const {
// ==== You SHOULD IMPLEMENT appropriate comparison here!!! ====
// Implementation will depend on type of QVariant values you use
//return v1 < v2;
}
};
并这样使用QVariantCompare
:
std::map<QVariant, int, QVariantLessCompare> m_testMap;
一个更典型的解决方案是使用 QMap
,它正确地实现了大多数 QVariant
类型的比较。它不会开箱即用 userTypes()
,但这可能仍然适合您的应用程序。
由 Володин Андрей 提出的解决方案的更简洁版本可能如下所示:
struct QVariantLessCompare {
bool operator()(const QVariant& v1,const QVariant& v2) const
{
return v1.toInt() < v2.toInt();
}
};