Ошибка компилятора C2993

"идентификатор" : недопустимый тип для параметра шаблона не типа "параметр"

  • До C++20 невозможно объявить шаблон со структурой, классом или аргументом объединения. Указатели можно использовать вместо этих типов в качестве параметров шаблона.
  • Так как C++20, структура, класс или объединения можно использовать в качестве параметров шаблона, не относящихся к типу. Параметр шаблона, отличный от типа, не может быть ссылочным типом rvalue или пакетом параметров типов rvalue.

Следующий пример приводит к возникновению ошибки C2993:

// compile with: /c and /std:c++17
template <int&& I>   // C2993
struct S1 {};

template <int&&... Is>   // C2993
struct S2 {};

Перед MSVC 19.26 следующий код был представлен C2993. Теперь он выдает C7582:

// compile with: /c /std:c++17
struct MyStruct {};

template <class T, MyStruct S>   // Was C2993 prior to MSVC 19.26. Now emits C7582.
class MyClass1 {};

template <class T, MyStruct* S>   // OK
class MyClass2 {};

С помощью C++17 и более ранних версий нельзя использовать параметры шаблона с плавающей запятой, отличные от типа. Так как C++20 разрешены параметры шаблона с плавающей запятой, отличные от типа. Используйте аргумент функции, чтобы передать параметр шаблона, отличного от типа с плавающей запятой, в шаблоны функций.

Перед MSVC 19.26 следующий код был представлен C2993. Теперь он выдает C7582:

// C2993b.cpp
// compile with: /c /std:c++17
template<class T, float F>   // Was C2993 prior to MSVC 19.26. Now emits C7592
void func1(T t) {}

template<class T>   // OK
void func2(T t, float F) {}