1

Possible Duplicate:
Overloading by return type

Why can't I declare three member functions like this:

  void x(int a);
  void x(String a); 
  int x(String a);

?

Community
  • 1
  • 1
pslayer89
  • 307
  • 5
  • 14

2 Answers2

7

Because you can't overload by return type.

void x(string a)

and

int x(string a)

have the same signature. The signature is made of:

  • function name
  • parameters
  • cv-qualifiers

Which, in your case, are the same.

Luchian Grigore
  • 253,575
  • 64
  • 457
  • 625
3

C++ does not allow you to overload functions based on the return type. Function overloading is only allowed based on the type of the arguments. This means that void x(String a) and int x(String a) are seen as the same function as far as overloading rules are concerned.

One important case that may be confusing (but is often used) is when const is put at the end of a member function. That would look something like int number_of_peanuts(bool tasty_only) const. That const at the end means that the class that this member function is part of cannot be modified by this function.

However, this is actually just a special case of argument type overloading. When you have a member function that is not declared static, there is implicitly an extra parameter added to your function, this this pointer. This means that the example function I gave is roughly equivalent to int number_of_peanuts(Class const * this, bool tasty_only). If you didn't have const at the end of the function, then instead it would be like int number_of_peanuts(Class * this, bool tasty_only).

So to summarize, the type and number of arguments are the only thing that allow you to overload. If you pass by value, as in void x(int a), then const won't give you overload opportunities, because the outside world cannot tell the difference between whether you modify your copy or not. If you pass by reference or pass a pointer, then you can use const with the thing they are referring to as overload options, so void x(std::string & a) and void x(std::string const & a) are different, because the world can tell if you modify a or not. Putting const at the end of the function is another source of overload opportunity. And finally, and most obviously, void x(int a) and void x(int a, int b) is a legal overload because you have a different number of arguments.

David Stone
  • 26,872
  • 14
  • 68
  • 84
  • 2
    cv-qualifiers (`const` and `volatile`) are already included in my answer. For instance, `void x(String const & a)` and `void x(String & a)` are different because the argument types are different. If you are talking about member-function `const`, so `void x(String a) const`, then that is also a special case of argument-type overloading. The `const` at the end means that the implicit `this` parameter (the pointer to the class, which is implicitly passed as the first argument to the function) is a `MyClass const * this` instead of a `MyClass * this`. – David Stone May 17 '12 at 14:18
  • A cv-qualifier applied to the function modifies the function signature. The fact that under-the-hood it converts this to a const pointer is an implementation detail. – Luchian Grigore May 17 '12 at 14:20
  • I agree with you, but a beginner (which the OP obviously is) might not find it so clear, so pointing it out in the actual answer might be very helpful. – Luchian Grigore May 17 '12 at 14:20
  • Actually it changes how the function is used. For instance, try using a member function with `bind`. If you attempt to bind `int` to the first argument of the function, you'll get a very long and confusing compiler error message. I'll edit to emphasize this point. – David Stone May 17 '12 at 14:22