在下面的例子中,我重载了uint8_t
和bool
的转换函数。并使用一个pair作为Map键boost::hash
。之前有一个错误ambiguity in conversion of 'const Mem' to 'float'
(不知道为什么它请求Mem -> float
转换),所以我决定为==
操作符添加一个重载。如果我只为==
运算符实现成员运算符重载,这将在clang++中给予编译错误。
In file included from /opt/compiler-explorer/gcc-11.2.0/lib/gcc/x86_64-linux-gnu/11.2.0/../../../../include/c++/11.2.0/iostream:39:
In file included from /opt/compiler-explorer/gcc-11.2.0/lib/gcc/x86_64-linux-gnu/11.2.0/../../../../include/c++/11.2.0/ostream:38:
In file included from /opt/compiler-explorer/gcc-11.2.0/lib/gcc/x86_64-linux-gnu/11.2.0/../../../../include/c++/11.2.0/ios:40:
In file included from /opt/compiler-explorer/gcc-11.2.0/lib/gcc/x86_64-linux-gnu/11.2.0/../../../../include/c++/11.2.0/bits/char_traits.h:39:
In file included from /opt/compiler-explorer/gcc-11.2.0/lib/gcc/x86_64-linux-gnu/11.2.0/../../../../include/c++/11.2.0/bits/stl_algobase.h:64:
/opt/compiler-explorer/gcc-11.2.0/lib/gcc/x86_64-linux-gnu/11.2.0/../../../../include/c++/11.2.0/bits/stl_pair.h:467:51: error: use of overloaded operator '==' is ambiguous (with operand types 'const Mem' and 'const Mem')
{ return __x.first == __y.first && __x.second == __y.second; }
为什么我需要==
的非成员重载,因为__x
和__y
是相同的类型,可以从成员操作符支持。Example run
#include <iostream>
#include <cstdint>
#include <unordered_map>
#include <string>
#include <boost/functional/hash.hpp>
struct Mem {
bool inv : 1;
uint8_t bit : 3;
Mem(bool v = false, uint8_t bs = 0) : inv(v), bit(bs) {}
operator uint8_t() const
{
return (bit << 1 | inv);
}
operator bool() const
{
return inv;
}
// not working for member overloading
bool operator==(const Mem& other)
{
return inv == other.inv;
}
};
// only work for non-member overload
// inline bool operator==(const Mem& lhs, const Mem& rhs)
// {
// return lhs.inv == rhs.inv;
// }
inline std::size_t hash_value(const Mem& mem)
{
return mem.bit;
}
int main()
{
std::unordered_map<std::pair<std::string, Mem>, std::string,
boost::hash<std::pair<std::string, Mem>>> map {};
auto i = Mem();
std::string k = "T";
auto p = map.find({k, i});
return 0;
}
1条答案
按热度按时间erhoui1w1#
您的成员
operator==
需要声明为const
(就像您的其他成员运算符一样),例如:如果不这样做,则当
==
比较的 * 左手 * 操作数是const Mem
对象时,将忽略成员operator==
。可以使用非成员operator==
,因为它的lhs
参数接受const Mem&
对象引用,该引用接受非常量Mem
和const Mem
对象。