3

I have looked at all the answers for the suggested related questions that stack overflow presented as I wrote this question, I have googled around, and I have looked at STL's video on overload resolution to try and figure out what makes the following code select the char const* overload over the template, but I can't figure it out.

#include <cstdio>

void foo( int i, char const* c_str_1, char const* c_str_2 )
{
   printf( "foo( int i, char const* c_str_1, char const* c_str_2 )\n" );
}

template< std::size_t N, std::size_t M >
void foo( int i, char const (&c_str_1)[N], char const (&c_str_2)[M] )
{
   printf( "foo( int i, char const (&c_str_1)[N], char const (&c_str_2)[M] )\n" );
}


int main( int argc, char* argv[] )
{
   char const* c_strg_1 = "This is a c style string.";
   foo( 1, c_strg_1, "bla" );
   foo( 1, "bla", "bla" );
   return 0;
}

It probably is something obvious I am missing, but the compiler always selects the char const* overload. I would have thought the template is an exact match and the other one needs a "decay"/"conversion".

Anyhow, thanks to anyone with insight into this.

ghlecl
  • 3,127
  • 1
  • 16
  • 15
  • Notable, of those two invokes, the only one that *could* be a match to your template is the second. The first is obviously not, and could never be. – WhozCraig Feb 02 '18 at 19:36
  • You could also be explicit: `foo<>(1, "bla", "bla");` – txtechhelp Feb 02 '18 at 19:39
  • @Barry After posting, I continued looking into this and I have also found this answer (https://stackoverflow.com/questions/43732122/why-is-literal-encouraged-to-decay-to-const-char-in-c-argument-type-mat) which could be considered a duplicate. I think I should hit the "That solved my problem" button to accept the duplicate and close the question, but the button does not appear. Sorry – ghlecl Feb 02 '18 at 20:27

1 Answers1

3

During the overload resolution usual functions are always preferred over function templates.

It means, that if there is an overload of foo which might accept appropriate arguments (even if the function template seems to be a better match), then the compiler will choose this overload.

In addition to that, for the first call:

foo( 1, c_strg_1, "bla" );

there is no way to instantiate a function template as c_strg_1 has a type of const char*.

Edgar Rokjān
  • 17,245
  • 4
  • 40
  • 67