The following does not compile on GCC 9.1 (which supports class non-type template parameters)
struct S { int i; };
template<S s>
struct T {};
int main()
{
T<{0}> x{};
}
The compiler reports error: could not convert '{0}' from '<brace-enclosed initializer list>' to 'S' despite the template argument s being of concrete type S.
T<S{0}> x{};
works as expected, but will C++2a allow the concrete type name S to be omitted, as is the case in other parts of the language?
will C++2a allow the concrete type name S to be omitted?
No.
[temp.arg.nontype]/2A template-argument for a non-type template-parameter shall be a converted constant expression (
[expr.const]) of the type of the template-parameter.
In T<{0}>, {0} is not an S: it is not an expression of the type of the template-parameter (S). {0} would be an initializer list (in a context where it would be allowed).
Bonus:
[dcl.init.list]/4List-initialization can occur in direct-initialization or copy-initialization contexts; list-initialization in a direct-initialization context is called direct-list-initialization and list-initialization in a copy-initialization context is called copy-list-initialization.
No initialization occur for template-arguments (unless when it does, see [temp.arg.nontype]/1).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With