26

How does C++ handle function overloading in this case?

#include <iostream>

void func(int x)
{
   std::cout << "integer";
}

void func(short x)
{
   std::cout << "short";
}

int main(void)
{
   func(3);
}

Output: integer

Why is that?

10
  • 50
    Because 3 is integer. Commented Aug 8, 2017 at 9:19
  • 3
    Possible duplicate of How do I write a short literal in C++?
    – jpmc26
    Commented Aug 8, 2017 at 22:31
  • 1
    The answers are correct, but don’t say why. C++ does this for backward-compatibility with C. Historically, C was designed on 16-bit DEC PDP machines and the first versions of it had no short type. As it got ported to new architectures and standardized, C kept the assumption that int is the native word length, and the most convenient default size to work with. This is also the reason for char and other types narrower than int getting automatically converted to int in some situations: this is faster on many machines, including the PDP.
    – Davislor
    Commented Aug 8, 2017 at 23:22
  • 2
    @Davislor: And yet that is approximately the rule. Integral literals have the smallest type from int, long, long long. The inconsistency is that short is missing from that list.
    – MSalters
    Commented Aug 9, 2017 at 7:39
  • 1
    A quick way to check the type is to output typeid(3).name() (you must #include <typeinfo> for this to work. The result would be i in this case. If you cast it to short, you'd see s instead.
    – Jir
    Commented Aug 9, 2017 at 7:56

5 Answers 5

58

Constants have types too. And without a suffix to indicate otherwise, 3 is simply an int constant. The compiler will choose a larger type if the constant is too big, but it won't go for things smaller than an int by default.

Now, it just so happens, that there is no suffix to make a short constant. You'd need to add a cast if you want that particular overload to be called.

2
29

Literal 3 is a constant and implicitly is of type int by the language design.

For your short overloaded function execution you have to use short variable:

short s = 3;
fun(s);

or cast the constant properly:

fun((short)3);
fun(static_cast<short>(3));

Type short hasn't suffix like for example long (long l = 42L;), but you can create one.

17

Because 3 is an integer.

fun(static_cast<short>(3));

would call the short version.

Or you can use user-defined literals to make a short: See here

6

You are doing

fun(3);

and 3 is a literal constant integer so the function that better matches the overload is this one

void fun(int x)
{
    std::cout << "integer";
}

feel free to play a litte with the types and casting those like:

fun(short(3));
fun(int(3));
// C++11
auto x = 3;
fun(x);
6

The constant 3 has it's own type, in this case it's an int. You need to explicitly cast your constant to short if you want your overload to execute

fun((short)3);

Not the answer you're looking for? Browse other questions tagged or ask your own question.