Stilllegung des Forums
Das Forum wurde am 05.06.2023 nach über 20 Jahren stillgelegt (weitere Informationen und ein kleiner Rückblick).
Registrierungen, Anmeldungen und Postings sind nicht mehr möglich. Öffentliche Inhalte sind weiterhin zugänglich.
Das Team von spieleprogrammierer.de bedankt sich bei der Community für die vielen schönen Jahre.
Wenn du eine deutschsprachige Spieleentwickler-Community suchst, schau doch mal im Discord und auf ZFX vorbei!
Werbeanzeige
Wäre es nicht besser, die Sache mit dem vector in einem eigenen Foo Container zu kapseln, anstatt so umständlich mit irgendwelchen virtuellen Methoden und wild überladenen operator== rumzumachen?
Ich hatte früher mal die Frage gestellt warum Operatoren Global überladen werden (Bei Klassen des selben Typs).
Das wäre jetzt für mich der einzige Grund das Global zu machen (meine damalige Frage konnte für mich nie zufriedenstellend beantwortet werden).
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 |
bool operator ==(const A& a, int x) // das würde auch als Member gehen { ... } bool operator ==(int x, const A& a) // das nicht { return a == x; } |
Wäre es nicht besser, die Sache mit dem vector in einem eigenen Foo Container zu kapseln, anstatt so umständlich mit irgendwelchen virtuellen Methoden und wild überladenen operator== rumzumachen?
Nein, weil ich Momentan alle meine Foo Unterklassen in separate Container speichere, und die alle eine identische Funktionsweise haben. Würde ich eine compare Methode in den Container einbauen wollen, müsste ich das ganze polymorph gestalten, was absolut nicht in meinem Interesse ist.
Ich könnte natürlich auch per Funktionspointer eine compare Methode an den Container übergeben, aber das ist irgendwie einfach nur umständlich.
Es ist ja keine Schande etwas falsch zu machen, als Programmierer tu ich das täglich, [...].
Ich hatte früher mal die Frage gestellt warum Operatoren Global überladen werden (Bei Klassen des selben Typs).
Das wäre jetzt für mich der einzige Grund das Global zu machen (meine damalige Frage konnte für mich nie zufriedenstellend beantwortet werden).
Es wäre immernoch gut zu wissen, was deine Foo- und Bar-Klassen repräsentieren. Wenn du wirklich Anregungen erhalten willst, wie du vorgehen könntest, dann brauchen wir diese Informationen, da es sonst eher ein rumgerate ist.
Mir kommt die ID der Element sehr komisch vor. Sie entspricht immer der Position des Elements in der Liste, unter Verrechnung eines konstanten Werts, wodurch dieser Wert faktisch redundant gespeichert wird. Über die Position in der Liste ergibt sich die ID.
Wenn an einer anderen Stelle außerhalb neue Objekte erstellt und mit einer ID versehen werden, dann müsste der Aufrufenden Stelle auch die "Seiteneffekte" bekannt sein (Überschreiben "zufälliger" Daten) bzw. die ID muss auf irgendeine Weise richtig bestimmt werden. Ist letzteres der Fall, wovon ich ausgehe, wäre es vielleicht sinnvoller, das richtige Element aus der Liste abzurufen und dieses zu verwenden. Wenn im Zuge dessen Änderungen durchgeführt werden, dann wurden Änderungen durchgeführt und das Flag kann gesetzt werden. (Idealerweise wird dieses Flag intern gesetzt, wenn die Änderungen durchgeführt werden.)
@Dot
Ich hatte früher mal die Frage gestellt warum Operatoren Global überladen werden (Bei Klassen des selben Typs).
Das wäre jetzt für mich der einzige Grund das Global zu machen (meine damalige Frage konnte für mich nie zufriedenstellend beantwortet werden).
Damit ist dein Bsp. schon aus dem rennen!
Link zur alten Diskusion
Es ist ja keine Schande etwas falsch zu machen, als Programmierer tu ich das täglich, [...].
Ich gehe mal davon aus, dass die Bearbeitung der Daten über einen Dialog stattfindet, bei dem auch ein "Abbrechen"-Button vorhanden ist. Ist das der Fall kann man so vorgehen, dass das jeweilige Objekt abgerufen wird, die zu bearbeitenden Informationen in die UI-Elemente übertragen werden, und erst beim Speichern die Änderungen im UI wieder auf das Objekt übertragen werden.
Aber egal wie man vorgeht, damit für ein bestimmtes Element der richtige Dialog zur Bearbeitung angezeigt werden kann, muss bereits der richtige Typ bekannt sein. Selbst wenn man für die Bearbeitung im UI eine Kopie des ursprünglichen Objekts anlegt, beim Speichern _kennt_ man die beiden Typen und kann dementsprechend einen für genau diesen Typ implementierten Operator verwenden.
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 |
//Basisklasse für Spieler und Bälle class GameObject { public: int xPos, yPos;//Position int xVel, yVel;//Geschwindigkeit. X-Komponente wird für Player nicht benutzt public: GameObject(); GameObject(int xPos, int yPos); bool operator==(const GameObject& rhs) const; bool CollidesWith(const GameObject& Other, int RadiusSum) const; void ProcessCollision(GameObject& Other); }; bool GameObject::operator==(const GameObject& rhs) const { if(xPos != rhs.xPos) return false; if(yPos != rhs.yPos) return false; if(xVel != rhs.xVel) return false; if(yVel != rhs.yVel) return false; return true; } class Player : public GameObject { public: int LastKeys; //Welche Tasten letzten Frame ausgeführt wurden int Score; //Punkte bool Scores; //Hat er gerade einen Punkt gemacht public: Player(); void ResetPosition(int Player); bool operator==(const Player& rhs) const; }; bool Player::operator==(const Player& rhs) const { if(!GameObject::operator==(rhs)) return false; if(LastKeys != rhs.LastKeys) return false; if(Score != rhs.Score) return false; if(Scores != rhs.Scores) return false; return true; } |
Werbeanzeige