[over.ics.rank] (original) (raw)
12 Overloading [over]
12.4 Overload resolution [over.match]
12.4.4 Best viable function [over.match.best]
12.4.4.3 Ranking implicit conversion sequences [over.ics.rank]
This subclause defines a partial ordering of implicit conversion sequences based on the relationshipsbetter conversion sequenceandbetter conversion.
If an implicit conversion sequence S1 is defined by these rules to be a better conversion sequence than S2, then it is also the case that S2 is aworse conversion sequencethan S1.
If conversion sequence S1 is neither better than nor worse than conversion sequence S2, S1 and S2 are said to beindistinguishable conversion sequences.
Two implicit conversion sequences of the same form are indistinguishable conversion sequences unless one of the following rules applies:
- List-initialization sequence L1 is a better conversion sequence than list-initialization sequence L2 if
- L1 converts to std::initializer_list<X> for some X andL2 does not, or, if not that,
- L1 and L2 convert to arrays of the same element type, and either the number of elements initialized by L1is less than the number of elements initialized by L2, or andL2 converts to an array of unknown bound and L1 does not,
even if one of the other rules in this paragraph would otherwise apply.
[Example 1: void f1(int); void f1(std::initializer_list<long>); void g1() { f1({42}); } void f2(std::pair<const char*, const char*>); void f2(std::initializer_liststd::string\); void g2() { f2({"foo","bar"}); } — end example_]
[_Example 2: void f(int (&&)[] ); void f(double (&&)[] ); void f(int (&&)[2]); f( {1} ); f( {1.0} ); f( {1.0, 2.0} ); f( {1, 2} ); — _end example_]
- Standard conversion sequenceS1is a better conversion sequence than standard conversion sequenceS2if
- S1is a proper subsequence ofS2(comparing the conversion sequences in the canonical form defined by [over.ics.scs], excluding any Lvalue Transformation; the identity conversion sequence is considered to be a subsequence of any non-identity conversion sequence) or, if not that,
- the rank ofS1is better than the rank ofS2, orS1andS2have the same rank and are distinguishable by the rules in the paragraph below, or, if not that,
- S1 and S2 include reference bindings ([dcl.init.ref]) and neither refers to an implicit object parameter of a non-static member function declared without a ref-qualifier, and S1 binds an rvalue reference to an rvalue and S2 binds an lvalue reference
[Example 3: int i;int f1();int&& f2();int g(const int&);int g(const int&&);int j = g(i); int k = g(f1()); int l = g(f2()); struct A { A& operator<<(int);void p() &;void p() &&;}; A& operator<<(A&&, char); A() << 1; A() << 'c'; A a; a << 1; a << 'c'; A().p(); a.p(); — _end example_]
or, if not that, - S1 and S2 include reference bindings ([dcl.init.ref]) andS1 binds an lvalue reference to a function lvalue and S2 binds an rvalue reference to a function lvalue
[Example 4: int f(void(&)()); int f(void(&&)()); void g();int i1 = f(g); — _end example_]
or, if not that, - S1 and S2 differ only in their qualification conversion ([conv.qual]) and yield similar types T1 and T2, respectively, where T1 can be converted to T2 by a qualification conversion.
[Example 5: int f(const volatile int *);int f(const int *);int i;int j = f(&i); — _end example_]
or, if not that, - S1andS2include reference bindings ([dcl.init.ref]), and the types to which the references refer are the same type except for top-level cv-qualifiers, and the type to which the reference initialized byS2refers is more cv-qualified than the type to which the reference initialized byS1refers.
[Example 6: int f(const int &);int f(int &);int g(const int &);int g(int);int i;int j = f(i); int k = g(i); struct X { void f() const;void f();};void g(const X& a, X b) { a.f(); b.f(); } — _end example_]
- User-defined conversion sequenceU1is a better conversion sequence than another user-defined conversion sequenceU2if they contain the same user-defined conversion function or constructor or they initialize the same class in an aggregate initialization and in either case the second standard conversion sequence ofU1is better than the second standard conversion sequence ofU2.
[Example 7: struct A { operator short();} a;int f(int);int f(float);int i = f(a); — _end example_]
Standard conversion sequences are ordered by their ranks: an Exact Match is a better conversion than a Promotion, which is a better conversion than a Conversion.
Two conversion sequences with the same rank are indistinguishable unless one of the following rules applies:
- A conversion that does not convert a pointer or a pointer to member toboolis better than one that does.
- A conversion that promotes an enumeration whose underlying type is fixed to its underlying type is better than one that promotes to the promoted underlying type, if the two are different.
- If classBis derived directly or indirectly from classA, conversion ofB*toA*is better than conversion ofB*tovoid*, and conversion ofA*tovoid*is better than conversion ofB*tovoid*.
- If classBis derived directly or indirectly from classAand classCis derived directly or indirectly fromB,
- conversion ofC*toB*is better than conversion ofC*toA*,
[Example 8: struct A {};struct B : public A {};struct C : public B {}; C* pc;int f(A*);int f(B*);int i = f(pc); — _end example_] - binding of an expression of typeCto a reference to typeBis better than binding an expression of typeCto a reference to typeA,
- conversion ofA::*toB::*is better than conversion ofA::*toC::*,
- conversion ofCtoBis better than conversion ofCtoA,
- conversion ofB*toA*is better than conversion ofC*toA*,
- binding of an expression of typeBto a reference to typeAis better than binding an expression of typeCto a reference to typeA,
- conversion ofB::*toC::*is better than conversion ofA::*toC::*, and
- conversion ofBtoAis better than conversion ofCtoA.
[Note 1:
Compared conversion sequences will have different source types only in the context of comparing the second standard conversion sequence of an initialization by user-defined conversion (see [over.match.best]); in all other contexts, the source types will be the same and the target types will be different.
— _end note_]
- conversion ofC*toB*is better than conversion ofC*toA*,