#ifdef WITH_CONCEPT
# include
# define CONCEPT std::same_as
#else
# define CONCEPT
#endif
template
//requires(sizeof...(Ns) > 0) // workaround
struct Foo {
static_assert(sizeof...(Ns) > 0);
static constexpr auto cnt = sizeof...(Ns);
static constexpr auto cnt0 = (0u + ... + (Ns == 0));
constexpr Foo() requires(cnt0 == 0) {}
constexpr explicit(cnt0 == 1)
Foo(CONCEPT auto...args)
requires(cnt0 > 0 && cnt0 == sizeof...(args))
{}
};
template void func() {}
int main() {
// This is okey, but would have same problem if `auto` is replaced with `Foo`
constexpr auto F = Foo{};
// Some compilers instantiate Foo which has hard error
func();
}
No WITH_CONCEPT WITH_CONCEPT
Clang
GCC
MSVC
Что говорит об этом стандарт?
Изменить: Частично сокращено до Всегда ли построение NTTP происходит для CTAD, даже если значение типа этой специализации задано?
Вывод Clang:
:11:19: error: static assertion failed due to requirement 'sizeof...(Ns) > 0'
11 | static_assert(sizeof...(Ns) > 0);
| ^~~~~~~~~~~~~~~~~
:18:24: note: in instantiation of template class 'Foo' requested here
18 | constexpr explicit(cnt0 == 1)
| ^
:31:10: note: while substituting deduced template arguments into function template '' [with Ns = (no value), args:auto = ]
31 | func();
| ^
:31:5: note: while substituting explicitly-specified template arguments into function template 'func'
31 | func();
| ^
:11:33: note: expression evaluates to '0 > 0'
11 | static_assert(sizeof...(Ns) > 0);
| ~~~~~~~~~~~~~~^~~
1 error generated.
Подробнее здесь: https://stackoverflow.com/questions/790 ... t-is-given