3

I wrote a small code:

#include<type_traits>

using namespace std;

template<typename T>
struct M{
    /*explicit*/ M(const T*) {}
};

template<typename T>
M<T> f(const M<T>&) {return M<T>();}

int main() {
    M<char> s1 = f<char>("Hello"); // OK
    M<char> s2 = f("Hello"); // error
    M<char> s3 = f(decay<char*>("Hello")); // error
    return 0;
}

Well the first s1 successfully compiles, although if I change M::M to explicit, it will also fail. But s2 and s3 fail to compile, even when I use decay<char*> on s3.


The difference is whether I specified template initialization argument type for f or not. Why do s2 and s3 fail to compile, any principles behind this in the C++ standard?

If I change main function to like this:

int main()
{
    M<char> s1=f<char>("Hello");//OK
    const char* p="hello";
    M<char> s2=f(p);//error
    M<char> s3=f(decay<const char*>("Hello"));//error
    return 0;
}

It still fails.

Why?

1
  • Try to put yourself in the compiler's shoes. Explain how, in s2 case, given the function parameter being const char[6] the compiler can conclude that the template parameter must be char. P.S. Your decay is wrong. const char[6] decays to const char *, and not char *. Commented Jun 29, 2016 at 1:47

1 Answer 1

3

Because template type argument deduction does not consider implicit conversions.

Type deduction does not consider implicit conversions (other than type adjustments listed above): that's the job for overload resolution, which happens later.

For the 2nd case, compiler can't match M<T> with const char [6], the function template is just ignored before overload resolution.

The 3rd case fails because "Hello" (i.e. const char [6]) can't be converted to decay<char *>. You might mean typename decay<char*>::type, but it still won't compile for the same reason of the 2nd case.

Sign up to request clarification or add additional context in comments.

2 Comments

If "T" means any type, why M<T> cannot match T to "const char [6]"?
@HindForsum T can match, but the parameter type is M<T>, which can't match.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.