2010-03-28 8 views
8

i-Klasse mit int Variablen x und y in privaten gegeben worden war, und eine Operator Überlastfunktion,Frage „dieser“ Zeigers in c in Bezug auf ++

class Bag{ 
private: 
    int x; 
    int y; 
public: 
    Bag(); 
    ~Bag(); 
    //....... 
    //.....etc 
}; 


Bag operator+ (Bag new) const{ 
    Bag result(*this); //what does this mean? 
    result.x += new.x;   
    result.y += new.y; 
} 

Was die Wirkung des mit „Bag Ergebnis (* Diese) Dort?.

+5

Ist die Funktion 'operator +' fehlt eine 'return' Anweisung? –

+3

Das sieht nicht wie gültiges C++ aus - neu ist das Schlüsselwort – Artyom

+0

Wenn Sie Operatoren erstellen möchten, schlage ich vor, 'Boost.Operators' zu betrachten. Sie haben ähnliche Operatoren zusammen gruppiert (wie '+ =' und '+') und schreiben nur einen der Gruppe die anderen kostenlos zur Verfügung :) –

Antwort

10

Bag result(*this) erstellt eine Kopie des Objekts, auf dem die Operatorfunktion aufgerufen wurde.

Beispiel, wenn es:

sum = op1 + op2; 

dann result wird eine Kopie von op1 sein.

Da die operator+ Funktion eine Summe ihrer Operanden macht und die Summe zurückgibt, brauchen wir einen Weg, um auf den Operanden op1 zuzugreifen, der über den this Zeiger erfolgt.

Alternativ könnten wir getan haben:

Bag result; 
result.x = (*this).x + newobj.x; // note you are using new which is a keyword. 
result.y = (*this).y + newobj.y; // can also do this->y instead 
return result; 
2

Die operator+ Funktion gibt eine Kopie. Die Aussage:

Bag result(*this); 

macht eine Kopie von dieses Objekt an den Aufrufer zurück. Gemäß der Signatur muss ein Wert zurückgegeben werden, sodass eine Kopie erstellt und das Objekt new hinzugefügt wird.

4

Erstens, sagen Sie dem Code-Writer nicht new als Variablennamen zu verwenden - es ist ein Schlüsselwort. Denken Sie auch an return result;. Und entweder durch const-Referenz übergeben oder direkt die new Tasche ändern.


Innerhalb einer Struktur/Klasse, this ist ein Zeiger auf sich. Daher ist *this eine Referenz auf die gesamte Bag-Instanz selbst.

Die Anweisung Bag result(a_bag_reference) den Copykonstruktor von Bag, rufen die eine Kopie von a_bag_reference in result macht.

Daher

Bag result(*this); 

macht eine Kopie von sich selbst, dann in result speichern. Dies macht die nächsten 2 Aussagen

result.x += new.x; 
result.y += new.y; 

wirken sich nicht auf die Instanz selbst (das heißt this->x und this->y konstant gehalten werden).

5

Ihr Code würde wie folgt aussehen:

class Bag { 
public: 
    Bag(); 
    Bag(Bag const& other); // copy ctor, declared implicitly if you don't declare it 
    ~Bag(); 

    Bag operator+(Bag const& other) const; 

private: 
    int x; 
    int y; 
}; 

Bag Bag::operator+(Bag const& other) const { 
    Bag result (*this); 
    result.x += other.x;   
    result.y += other.y; 
    return result; 
} 

Das implizite „aktuelles Objekt“ für Elementfunktionen durch einen speziellen Wert mit dem Namen hingewiesen wird diese.Dann erhält *this das Objekt (durch Dereferenzierung dieses), und es wird verwendet, um (über den Kopierkonstruktor) einen anderen Beutel mit dem Namen Ergebnis zu konstruieren.

Ich vermute, dieser Code von einer Hausaufgabe genommen wird, so dass Sie möglicherweise nicht die one true addition operator Muster verwenden können, aber es ist üblich, und Sie sollten sich dessen bewusst sein:

struct Bag { 
    //... 
    Bag& operator+=(Bag const& other) { 
    x += other.x; 
    y += other.y; 
    return *this; // return a reference to the "current object" 
    // as almost all operator=, operator+=, etc. should do 
    } 
}; 

Bag operator+(Bag a, Bag const& b) { 
    // notice a is passed by value, so it's a copy 
    a += b; 
    return a; 
} 
+1

Das ist eine gefährliche Art zu schreiben op +() - der erste Parameter wird in Scheiben geschnitten und wenn in der darauf beruhenden Funktion ein polymorphes Verhalten beabsichtigt war, wird dies nicht der Fall sein. Es ist viel besser, beide Parameter als konstante Referenzen zu definieren und die Kopie innerhalb der Funktion zu erstellen. –

+0

@Neil: Kopiert innerhalb der Funktion auch Slices; Es ist viel besser, dieses Muster zu verwenden, bis Sie es ändern müssen. Siehe auch http://cpp-next.com/archive/2009/08/want-speed-pass-by-value/, das das gleiche Idiom für operator = fördert. –

2

Bag result(*this); ist eine Deklaration Variable result und Aufruf seiner Kopie Konstruktor.

Sie können sich vorstellen, dass C++ automatisch einen Standardkopiekonstruktor für alle Klassen deklariert. Seine Aufgabe ist es einfach, ein Objekt mit einem anderen Objekt zu initialisieren:

Bag::Bag(Bag const& src) { 
    x = src.x; 
    y = src.y; 
}

Der Ausdruck *this ein wenig beunruhigend aussehen kann, ist aber nur die üblichen Horror von C++, wenn Sie mit & Parameter beschäftigen.