我有一個類可以用一組附加模板來裝飾以提供附加功能。每個插件都有一個基類需要知道的標識addon_value。模板元編程OR操作
下面的代碼是我想要做的一個例子。顯然,main()函數無法編譯。目標是讓CBase :: GetValueOfAddOns()知道每個附加組件的addon_value的OR值。該計算實際上並不需要在GetValueOfAddOns()中執行,它只需要能夠得到結果。
template< class T >
class AddOn_A : public T
{
public:
AddOn_A(int x) : T(x)
{};
enum { addon_value = 0x00000001 };
};
template< class T >
class AddOn_B : public T
{
public:
AddOn_B(int x) : T(x)
{};
enum { addon_value = 0x00000010 };
};
class CBase
{
public:
explicit CBase(int x) : x_(x)
{
// error LNK2001: unresolved external symbol "public: virtual int __thiscall CBase::GetValueOfAddOns(void)const " ([email protected]@@UBEHXZ)
int z = GetValueOfAddOns();
};
virtual int GetValueOfAddOns() const = 0;
private:
int x_;
};
// define an empty AddOn
template<class> class empty
{
public:
enum { addon_value = 0x00000000 };
};
// forward declaration and Add-On defaults
template< template<class> class AddOn1 = empty,
template<class> class AddOn2 = empty,
template<class> class AddOn3 = empty >
class CMyClass;
// specialized template for the default case
template<> class CMyClass< empty, empty, empty > : public CBase
{
public:
CMyClass(int x) : CBase(x)
{};
enum { addon_value = 0x00000000 };
};
// actual definition
template< template<class> class AddOn1,
template<class> class AddOn2,
template<class> class AddOn3 >
class CMyClass : public AddOn1<CBase>,
public CMyClass< AddOn2, AddOn3 >
{
public:
CMyClass(int x) : AddOn1<CBase>(x),
CMyClass< AddOn2, AddOn3 >(x)
{};
enum { addon_value = AddOn1<CBase>::addon_value | CMyClass< AddOn2, AddOn3 >::addon_value };
int GetValueOfAddOns() const
{
return addon_value;
}
};
int _tmain(int argc, _TCHAR* argv[])
{
CMyClass<AddOn_A> A(0);
_ASSERT(A.GetValueOfAddOns() == AddOn_A<CBase>::addon_value);
CMyClass< AddOn_A, AddOn_B > AB(0);
_ASSERT(AB.GetValueOfAddOns() == (AddOn_A<CBase>::addon_value | AddOn_B<CBase>::addon_value));
return 0;
}
感謝您的幫助, PaulH
您不能從構造函數或析構函數調用虛擬方法。這是未定義的行爲。 – 2009-10-22 15:41:12
@Martin York - 那麼,有沒有辦法在CBase ctor()中獲得addon_value還是不合理? – PaulH 2009-10-22 15:49:11
Martin York:調用虛函數很好,除非它們是純粹的。混淆人的唯一原因是他們只會指向已構建的最衍生對象 - 這幾乎總是意味着調用實際上不是虛擬的。同樣對於析構函數 - 調用未完成其析構函數的大多數派生對象。 – coppro 2009-10-22 16:16:06