Please consider the following example:
// Mind the default template argument
template <typename T = int>
struct Test;
template <typename T>
struct Test
{
};
template <typename T>
struct Test;
int main()
{
Test<> t;
return 0;
}
The code above can be successfully compiled by MSVC 19, gcc 8 and clang 8. Just as expected.
Now let's move the default template argument to the definition of the class template:
template <typename T>
struct Test;
// Mind the default template argument
template <typename T = int>
struct Test
{
};
template <typename T>
struct Test;
int main()
{
Test<> t;
return 0;
}
This works with all three compilers, too.
However, if I placed the default argument after the definition of the Test class template, then Visual Studio would refuse to compile the source and complain that
line marked (!): too few template arguments
template <typename T>
struct Test;
template <typename T>
struct Test
{
};
// Mind the default template argument
template <typename T = int>
struct Test;
int main()
{
Test<> t; // (!)
return 0;
}
Is it a MSVC bug?
I think cppreference is quite clear on the subject: default template arguments on the definition and all declarations should be merged. No special exception is made for the declarations following the definitions, right?