В: Существуют ли какие-либо механизмы времени компиляции в C ++, которые я могу использовать для автоматической проверки соответствия набора методов класса шаблона от специализации класса к специализации?
Пример: Позвольте намПредположим, я хочу интерфейс класса, который имеет очень различное поведение в зависимости от специализации значения шаблона:
// forward declaration of template class name
template <typename T, bool isZero> class MyClass;
// partial class specialization for isZero = false case
template <typename T> class MyClass <T, false>
{
T _val;
public:
MyClass(T value) { _val = value; }
T GetValue(void) const { return _val; }
};
// partial class specialization for isZero = true case
template <typename T> class MyClass <T, true>
{
public:
MyClass(T value) {}
T GetValue(void) const {return T(0);}
};
Идея заключается в том, что при компиляции по вторникам MyClass.GetValue () возвращает 0, тогда как в любой другой деньнеделю мы получаем ожидаемое значение ... или что-то подобное.Детали и мотивы не важны.; -)
Теперь, хотя это кажется одним из способов достижения частичной специализации функции, основанной на частичной специализации класса, также кажется, что это также может быть полный хаос, потому что две специализации класса могут (AFAIK) иметь совершенно несовместимыеинтерфейсы.Если я на самом деле собираюсь использовать этот механизм в производственной среде, я хотел бы получить уведомление о времени идеальной компиляции, если я по ошибке добавлю некоторые методы к некоторым специализациям, а не другим, или где-нибудь забуду const и т. Д. Как мне это получить?
Что касается бонусных баллов, давайте предположим, что я не хочу, чтобы случайно позволить другим значениям isZero, кроме (true / false), скомпилироваться, как это может произойти, если я предоставлю универсальную реализацию MyClass и допустим такжеЯ с подозрением отношусь к дополнительным затратам времени исполнения от добавления виртуального здесь для чисто виртуальных методов базового класса.
Это кажется настолько очевидной языковой особенностью, что мне, вероятно, не хватает леса для деревьев здесь, и, возможно, яЯ уже получаю это поведение через какой-то механизм и еще не осознал этого.
> cat test.cpp
#include <stdio.h>
// forward declaration of template class name
template <typename T, bool isZero> class MyClass;
// partial specialization for isZero = false case
template <typename T> class MyClass <T, false>
{
T _val;
public:
MyClass(T value) { _val = value; }
T GetValue(void) const { return _val; }
};
// partial specialization for isZero = true case
template <typename T> class MyClass <T, true>
{
public:
MyClass(T value) {}
T GetValue(void) const {return T(0);}
};
int main( void )
{
MyClass<float, false> one(1);
MyClass<float, true> notOne(1);
printf( "%f, %f\n", one.GetValue(), notOne.GetValue());
return 0;
}
> clang -Wall -pedantic test.cpp
> ./a.out
1.000000, 0.000000