目标是编写一个元程序来确定一个类是否有任何虚函数,这是一项相当容易的任务。我的代码如下。
template <typename T>
class HasVirtual :
public T
{
public:
static const bool has_virtual;
virtual void doit() {}
};
template <typename T>
bool const HasVirtual<T>::has_virtual = sizeof(T) == sizeof(HasVirtual<T>);
我遇到的问题是,当我尝试在其他地方使用它时,就像这样:
template <typename T, bool isVirtual = HasVirtual<T>::has_virtual>
class PointerCopy
{
public:
static T *copy(const T *x)
{
return new T(*x);
}
};
template <typename T>
class PointerCopy<T, true>
{
public:
static T *copy(const T *x)
{
return x->copy();
}
};
即使使用error C2975: 'isVirtual' : invalid template argument for 'PointerCopy', expected compile-time constant expression
标识符定义has_virtual
,我也会收到错误static const
。我最后“作弊”并定义了另一个类:
template <typename T>
class VirtualDerived :
public T
{
public:
virtual void fun() {}
};
template <typename T>
class HasVirtual
{
public:
static const bool has_virtual = sizeof(T) == sizeof(VirtualDerived<T>);
};
完美无缺。不过,我想知道为什么我会遇到这个问题(或者这是Visual Studio 2012编译器的问题)。这似乎是合法的愚蠢:在类之外定义一个常量不应该使它不再是常数。