2011-05-23 49 views
0

如何繼承重載的運算符+()?繼承運算符+()

例如,我有兩類:

class Bin : public Number<2, 256> 
{ 
public: 
    Bin(const char* number = NULL) : 
     Number(number) 
    {} 
}; 

template <unsigned int BASE, unsigned int ORDER> 
class Number 
{ 
private: 
    ... 

public: 
    Number(const char* number = NULL) { 
     ... 
    } 

    const Number& operator +=(const Number& number) { 
     ... 
    } 

    Number operator +(const Number& number) const { 
     Number result = *this; 
     return result += number; 
    } 
}; 

操作者+()返回數量。但我想做的事:

Bin firstNum("101010111010"); 
Bin secondNum("1101011101"); 
Bin result = firstNum + secondNum; 

(firstNum + secondNum)的類型 - 數< 2,256>不濱。我必須在每個繼承者中重載+()嗎?

+0

請注意,這個問題並不特定於'operator +',甚至一般的操作符。對於「普通」成員函數也是如此...... – 2011-05-23 20:03:44

回答

0

無法做到,操作員不能被設爲虛擬(即繼承)。至少不是直接的。

你可以這樣做:

class Base { 
public: 
    Base operator+(const Base& addend) { return addOp(addend) ; } 
private: 
    virtual Base addOp(const Base& addend) ; 
} ; 

,然後覆蓋addOp你的心臟的內容。但是你需要確保繼承的任何東西都可以返回一個可以與其他任何東西一起工作的「基礎」。這很快就會變得非常複雜。

+0

將兩個派生類添加到「Base」時,可能會有些混淆。 – 2011-05-23 20:09:39

1

考慮在稍微複雜的示例中需要發生的情況,其中派生類Bin具有其自己的成員變量。基類函數怎麼可能知道怎麼做才能創建返回值?它在「混合模式」添加中會做什麼? (例如,如果一個參數是Bin,另一個是Blah)。

所以是的,你需要在任何地方定義特定的操作符,你需要特定的行爲。請注意,這不僅適用於重載運算符,還適用於一般成員函數。

+0

如果我想爲每個派生類定義自己的add運算符,我必須複製代碼。如何更清楚地解決這個問題? – Dmitry 2011-05-23 20:25:52

+1

很多很好的文檔。要更清楚一點,就像Oli說的那樣,如果你這樣做會發生什麼情況:定義一個Hex類,然後添加Bin和Hex? Number不知道任何一個類,所以你必須決定在派生類中做什麼:你是否返回一個Bin?十六進制?拋出錯誤?您仍然可以在Number中包裝和使用實現,但最終,您會在派生類中需要_need_代碼來解決此類問題。 – Matt 2011-05-23 20:56:56

1

在所有派生類中重複執行operator+可能會更容易。但是,如果您覺得冒險,則可以使用curiously recurring template pattern在您的Number模板類中強制執行類型一致性。