c++c++11implicit-conversionexplicit-conversion

compiler failed to apply explicit conversion to an expression used as a condition


Here is my code:

#include <iostream>

using namespace std;
class Sales{
  public:
    Sales(int i = 0):i(i){}
    explicit operator int(){ return i; }
  private:
    int i;
};

int main(){
  Sales s(5);
  if(s == 4) cout << "s == 4" << endl;
  else cout << "s != 4" << endl;
  return 0;
}

In c++ primer(5th), it says:

compiler will apply an explicit conversion to an expression used as a condition

But in this case, there is no such conversion. When I delete explicit, the code then works fine.

However, when I change
explicit operator int(){ return i; } to
explicit operator bool(){ return i != 0; },

and change if(s == 4) to if(s) respectively, then the code works fine.

Looks like the convesion rule is a little bit confusing, can anybody explain this in more detail?


Solution

  • Among implicit conversions, since C++11, the explicit user-defined conversion function will be considered for contextual conversions; which happens in the following contexts and when type bool is expected. For int, it's not applied.

    In the following five contexts, the type bool is expected and the implicit conversion sequence is built if the declaration bool t(e); is well-formed. that is, the explicit user-defined conversion function such as explicit T::operator bool() const; is considered. Such expression e is said to be contextually convertible to bool.

    controlling expression of if, while, for;
    the logical operators !, && and ||;
    the conditional operator ?:;
    static_assert;
    noexcept.