简体   繁体   中英

Operators for non-primitive boxed types

I have the following class definition:

template <typename T>
class MyBox {
public:
    MyBox(T value) { _value = value; }
    operator T() const { return _value;  }
private:
    T _value;
};

typedef MyBox<int> MyInt;
typedef MyBox<std::string> MyString;

When I try to use operators on my typedefs like this

bool first = MyInt(1) == MyInt(1);    // works
bool second = std::string(MyString("a")) == std::string(MyString("a"));    //works
bool third = MyString("a") == MyString("a");   // does not compile

the compiler complains about the third comparison

no operator "==" matches these operands. operand types are: MyString == MyString

and this happens with any other non-primitve boxing (eg MyBox<float> works but MyBox<std::map<int,int> > not. Why is that so?

This is especially unclear to me because for the first and second comparison the operator T() is used - why can't that be done automatically for MyString as well?

UPDATE: Is there a simple solution to this other than providing the specific operators for each non-primitive template? And what to do with MyString("a") == std::string("a") ?

The reasons on why it works for built-in types, but does't work for custom types is answered in the following SO quesiton: using user-defined conversions with implicit conversions in comparisons . In short, this is because type conversion does not happen for template-deduced types. And while built-in operator== for int is not a template (and thus can be found using type conversion when MyBox<int> is used), operator== for std::string is a template.

However, the question mentioned above doesn't have details on how to solve this problem. Here is how: add following free functions

template<class T>
bool operator==(const MyBox<T>& lhs, const MyBox<T>& rhs) {
    return static_cast<const T&>(lhs) == static_cast<const T&>(rhs);
}

template<class T>
bool operator==(const MyBox<T>& lhs, const T& rhs) {
    return static_cast<const T&>(lhs) == rhs;
}

template<class T>
bool operator==(const T& lhs, const MyBox<T>& rhs) {
    return lhs == static_cast<const T&>(rhs);
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM