2011-09-07 77 views
1

我需要在C++中重載*運算符。所以我創建了一個名爲Element的類,它必須重載此操作符以處理存儲在其中的double值。這是我在執行文件中所做的:運算符在C++中重載

#include "Element.h" 
#include <iostream> 

using namespace std; 

// Other code that is not relevant 

Element Element::operator * (const Element &obj) 
{ 
    d *= obj.d; 
    return *this; 
} 

這是行不通的。它拋出一個錯誤說:「不匹配 '運算符*' 在 '8 * C'

在主文件我有:

d = a = 8 * c - 4 + b; 

其中d,a,c和b是所有對象類Element

+2

我會推薦[運算符重載常見問題](http://stackoverflow.com/q/4421706/46642)。 –

+0

謝謝我會檢查出來 – Tim

+0

8不是'Element'。它被視爲一個整數。您顯示的代碼只允許兩個「元素」相乘。 – erikH

回答

3

你真的瞭解你在做什麼在這裏,你超載了「*」操作的元素c拉斯,但你這樣做,而期待另一個元素有一個'參數'。

你寫的其實是期待這種代碼的代碼

Element v, w, a; 
a = v * w; 

正如mentionned,你可能想看一看:http://www.learncpp.com/cpp-tutorial/92-overloading-the-arithmetic-operators/

+0

嗯好吧,我已經閱讀了一點在learCPP網站..我會嘗試和實現一些代碼寫在那裏..謝謝你的幫助 – Tim

1

那是因爲你只爲Element * Element重載運算符*,而c * 8你就必須實現Element Element::operator * (const int i)

+1

表達式是8 * c,成員操作符不會這樣做。 Op需要使用全局運算符重載和const Element和帶有參數化Element構造函數的引用。 –

+0

你會注意到我在我的文章中寫了'c * 8'。 –

0

您現有的運營商實現允許你乘兩個Element對象一起。 但是,根據'主文件'中的客戶端代碼,您需要能夠將Element對象乘以標量值; 8在這種情況下。

所以,你需要的是一個額外的操作,這需要雙重作爲它的參數: 類似以下內容:

Element Element::operator * (const double scalar) const 
{ 
    const Element e(d * scalar); 
    return e; 
} 

在這裏,我假設你的元素類有一個構造函數接受一個標量參數,並將其分配給d。

還請注意,您現有的operator *實現在語義上很奇怪, ,因爲它會改變d(帶* =)的內部狀態。 這是幾乎可以肯定不是你想要的...

1

你可以用一個非成員超載匹配8 * C的表達(INT,元素)像

Element operator* (const Element& leftHandSide, const Element& rightHandSide){ 
    return Element(leftHandSide.d * rightHandSide.d); 
} 

通過使用const Element&您可以利用的類型轉換的簽名類似Element::Element(int)的構造函數。

0

我有一個解決方案,併爲您的操作員超載警告。

解決方案:

#include <iostream> 
using namespace std; 

struct Element { 
    double d; 
    Element(double d) {this->d = d;} 
    Element operator*(const Element &obj) { 
     d *= obj.d; 
     return *this; 
    } 
}; 

Element operator*(const int i, const Element& e) { 
    return Element(static_cast<double>(i) * e.d); 
} 

ostream& operator<<(ostream& os, const Element& e) { 
    os << e.d; 
    return os; 
} 

int main() { 
     Element e(2); 
     cout << "Product of 8 and e: " << 8*e << '\n'; 

     // This shows why your overload is a bad idea: 
     Element a(3); 
     cout << "a is " << a << '\n'; // prints 3 
     cout << "Now its product with e is: " << a*e << '\n'; // prints 6 
     cout << "Surprise: a is now " << a << '\n'; // prints 6 
} 

你原來超載沒有工作,因爲它甚至沒有叫。您的表達是相似的

a = 8*c 

其中圖8是int類型的,並且當C++解析從離開這個表達式向右它看到圖8是int類型的,並試圖搜索運算符*的過載(常量元素& )在int類型中,它找不到它,導致它不知道,也不應該知道有關您自己的用戶定義類型的任何信息。所以如果你想讓你自己的類與其他類型進行交互,你需要將operator *的重載作爲成員函數嵌入到其他類型中,或者像我在解決方案中那樣將其聲明爲外部函數。

現在的警告。您的原始運算符重載不明確,導致它修改原始對象,這被認爲是意外行爲。我在上面的代碼中顯示了這一點。這就像乘以2 8會給你16,但在同一時間做16出你8.你真正想要做的是在你的乘法運算符來創建一個新的元素,並將其返回:

struct Element { 
    double d; 
    Element(double d) {this->d = d;} 
    Element operator*(const Element &obj) { 
     return Element(this->d * obj.d); 
    } 
}; 

哎呀這些答案需要很多時間...我應該工作,雖然:\