目标是编写一个元程序来确定一个类是否具有任何虚函数,这是一项相当容易的任务。我的代码如下。
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 编译器的问题)。这似乎有点愚蠢:在类之外定义一个常量不应该使它不再是一个常量。