acraig5075
acraig5075

Reputation: 10756

Precedence of overloaded cast operators

In the code below, I would expect to get a compiler error if more than one cast operator is defined because of the ambiguity.

#include <iostream>
#include <sstream>

struct A
{
    operator const char*() { return "hello world\n"; }
    operator float()       { return 123.0F; }
    //operator int()         { return 49; }
};

int main()
{
    A a;
    std::stringstream ss;
    ss << a;
    std::cout << ss.str();
    return 0;
}

Instead, as long as only one numeric cast operator is defined then it compiles with no errors, no warnings, and the numeric cast is used in preference to the operator const char *(). The order of the declared operators makes no difference.

However if operator int() and operator float() are both defined then I get what I expected from the start:

'operator <<' is ambiguous

Are there precedence rules for casts, or why does the compiler choose the numeric cast by default? I do understand that I should explicitly state which cast I mean, but my question is on the default choice the compiler makes.


Edit: Using compiler MSVC 2010

Upvotes: 14

Views: 462

Answers (1)

Andy Prowl
Andy Prowl

Reputation: 126522

Conversions are ranked according to § 13.3.3.1 of the C++ Standard. In particular, user-defined conversion sequences pertinent to your example are regulated by § 13.3.3.1.2/1:

"A user-defined conversion sequence consists of an initial standard conversion sequence followed by a user-defined conversion (12.3) followed by a second standard conversion sequence. [...] If the user-defined conversion is specified by a conversion function (12.3.2), the initial standard conversion sequence converts the source type to the implicit object parameter of the conversion function."

All conversions sequences here involve:

  1. a fictitious conversion to the source type of the implicit object parameter of the conversion function;
  2. a user-defined conversion;
  3. an identity conversion to the input type of operator <<.

These conversion sequences all have the same rank. Thus, the call should be ambiguous. If it is not, for me it is a compiler bug.

Upvotes: 4

Related Questions