Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Overload resolution C++ for const member functions

Assume you have a class T with two member functions

  1. char foo() const {...}
  2. char foo() {...}.

It is my understanding that when called for a constant T, we resolve to (1); and for a non-constant T, we resolve to (2). 

  1. is that correct?   
  2. which rule is invoked in this resolution? (reference to standard great, but a helpful brief summary appreciated) 

Notes:

  1. I tried to google for it, but old hits I got on SO were cases for other overload resolutions involving const. However, link to an old SO actually explaining the above obviously great.     

  2. This came up when re-reading Stroustrup's "The C++ programming language", 2nd edition ("Special Edition"), String/Cref example in section 11.12, p. 296. As Stroustrup is so precise, the answer might be in previous sections, but I fail to see where. Reference to sections in Stroustrup very welcome too (2nd edition best as this is the one I have). Section 10.2.6 introduces const members as those "that don't change an object's value", which hints at the answer, but doesn't strike me as a clear resolution directive.

like image 650
gnometorule Avatar asked Jan 30 '14 22:01

gnometorule


People also ask

Can const function be overloaded?

Overloading on the basis of const type can be useful when a function returns a reference or pointer. We can make one function const, that returns a const reference or const pointer, and another non-const function, that returns a non-const reference or pointer.

What is overload resolution?

The process of selecting the most appropriate overloaded function or operator is called overload resolution. Suppose that f is an overloaded function name. When you call the overloaded function f() , the compiler creates a set of candidate functions.

Can we overload member function in C Plus Plus?

You can overload both member functions and free functions. The following table shows which parts of a function declaration C++ uses to differentiate between groups of functions with the same name in the same scope.

Why we use const in operator overloading in C++?

The const qualifier ensures that the parameter (param) is not altered inside the operator=() method. The above method alters the right hand side operand 'param' after assigning the value to the left hand side operand. The const qualifier helps you not to violate the semantics of the assignment operation.


1 Answers

In N3242 (the standard draft I have on hand), 13.3.1 paragraph 4 says

the type of the implicit object parameter is "lvalue reference to cv X” for [non-static member] functions declared without a ref-qualifier or with the & ref-qualifier

this means that type of the implicit object argument, which occurs first, is an "lvalue reference to cv X", where X is the class, and cv is the cv-qualification of the member variable (i.e. const or non-const). Then, overload resolution continues as normal.

To review the overload resolution process, first, both are listed as "candidate" functions as they are in the correct scope and have the correct name.

In the const case, only the const member function gets to the next step (called "viability"), so it's automatically the best choice. The non-const member function is not viable because you can't convert a const reference into a non-const reference.

In the non-const case, both the const and non-const versions are viable, but the non-const one is "better" because of the fifth rule of 13.3.3.2 paragraph 3, quoted below.

Standard conversion sequence S1 is a better conversion sequence than standard conversion sequence S2 if ...

S1 and S2 are reference bindings, 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 by S2 refers is more cv-qualified than the type to which the reference initialized by S1 refers.

like image 167
rmcclellan Avatar answered Oct 16 '22 05:10

rmcclellan