Using clang 3.6.0, I am unable to compile the following code example.
#include <type_traits>
template <typename T> constexpr bool IS_SCALAR = ::std::is_scalar<T>::value;
template <typename T, bool = IS_SCALAR<T>>
struct Class_Breaks
{
};
template <typename T, bool = ::std::is_scalar<T>::value>
struct Class_Works
{
};
void function()
{
Class_Breaks<int> break_error;
Class_Breaks<int, IS_SCALAR<int>> breaks_ok;
Class_Works<int> ok;
}
But, the following error messages are returned:
1> [ 66%] Building CXX object CMakeFiles/Core.dir/tests.cpp.obj
1>D:\Projects\Core\Core\tests.cpp(4,30): error : non-type template argument is not a constant expression
1> template <typename T, bool = IS_SCALAR<T>>
1> ^
1> D:\Projects\Core\Core\tests.cpp(16,18) : note: while checking a default template argument used here
1> Class_Breaks<int> break_error;
1> ~~~~~~~~~~~~~~~~^
1> 1 error generated.
The body can contain no goto statements or try blocks. An explicit specialization of a non- constexpr template can be declared as constexpr: An explicit specialization of a constexpr template doesn't also have to be constexpr: The following rules apply to constexpr functions in Visual Studio 2017 and later:
Default template arguments Default template arguments are specified in the parameter lists after the = sign. Defaults can be specified for any kind of template parameter (type, non-type, or template), but not to parameter packs.
Each function template has a single function parameter whose type is a specialization of X with template arguments corresponding to the template parameters from the respective function template where, for each template parameter PP in the template parameter list of the function template, a corresponding template argument AA is formed.
If your purpose is just to shorten code a bit, in C++14 you can create variable template: GCC 5 will also support this. Show activity on this post. You tell the compiler, that addFunc would be a constexpr.
As mentioned by @StenSoft, it is a known bug. If you need to make it work because you have a constexpr
template variable you'd like to use as a default, you can wrap the default value into an std::intergral_constant
:
template<
typename T,
bool = std::integral_constant< bool, IS_SCALAR<T> >::value
>
Live example
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