doppelter speicherverbrauch
-
ich habe ein recht seltsames problem: wenn ich ein modell vom typ infantry in eine liste packe, meinetwegen so:
else if (conf_item == "models") { // cur_unit->addModel(new Infantry(abstrMBoss) ); for(int i = 0; i < conf_value.toInt(); i++) { Infantry *model = new Infantry(1.0); cur_unit->addModel(model); } std::cout<<"einheitengröße: "<<cur_unit->size()<<std::endl; }dann stimmt die einheitengröße in der liste. der witz ist aber, dass ich die unit übergeben muss:
else if (conf_item == "models") { // cur_unit->addModel(new Infantry(abstrMBoss) ); for(int i = 0; i < conf_value.toInt(); i++) { Infantry *model = new Infantry(1.0, cur_unit); // model->setOwner(cur_unit); cur_unit->addModel(model); } std::cout<<"einheitengröße: "<<cur_unit->size()<<std::endl; }und dann ist die liste immer exakt doppelt so groß wie sie sein dürfte.
ich vermute ganz stark dass es etwas damit zu tun hat, dass ich von der model-klasse erbe, aber, warum beeinflusst das den speicherverbrauch und wie umgeh ich das am besten. denn jeder 2. eintrag scheint datenmüll zu enthalten...ps: ich bin nicht so erfahren... also bitte rücksicht nehmen

class Model { public: Model(Unit *o = NULL) { owner_u = owner_u; } void inline sSet(bool s) {set = s;}; bool inline setting() {return set;}; void inline sSelect(bool s) {sel = s;}; bool inline selected() {return sel;}; void inline sMove(bool m) {mov = m;}; bool inline moving() {return mov;}; void inline setOwner(Unit *o) {owner_u = o; owner_u->addModel(this);}; Unit inline *owner() {return owner_u;}; QPointF inline position() {return pos;}; void inline move(double x, double y) {pos.setX(pos.x() + x); pos.setY(pos.y() + y);};// relative Bewegung void inline set_position(double x, double y){pos.setX(x); pos.setY(y);}; // absolute Positionsaenderung void inline set_position(QPointF p) {pos.setX(p.x()); pos.setY(p.y());}; // absolute Positionsaenderung virtual EModelType type() = 0; virtual double size() = 0; virtual double angle()= 0; virtual double height() = 0; virtual double width() = 0; virtual void face(double a) = 0; virtual void turn(double a) = 0; virtual void sTurn(bool t) = 0; virtual bool turning() = 0; private: QPointF pos; Unit *owner_u; bool sel; bool mov; bool set; }; class Infantry : public Model { public: Infantry(double d = 1.4, Unit *o = NULL) { sSelect(false); sMove(false); sTurn(false); sSet(false); diam = d; setOwner(o); }; double inline size() {return diam;}; EModelType inline type() { return MT_INFANTRY; }; double angle() {return -1;}; double height() {return -1;}; double width() {return -1;}; void face(double) {}; void turn(double) {}; void sTurn(bool) {}; bool turning() {return false;}; private: double diam; };
-
Hi spartaaa,
mir ist folgendes aufgefallen:
Infantry(double d = 1.4, Unit *o = NULL){ //... setOwner(o); }void inline setOwner(Unit *o) {owner_u = o; owner_u->addModel(this);};Hier erzeugst du, wenn du nur einen Parameter übergibst ein undefiniertes Verhalten,
da du owner_u NULL zuweist und dann auf dem (nicht vorhandenen) Objekt eine Funktion aufrufst.Und der Code schmiert wirklich nicht ab? ^^
Wenn du allerdings eine Unit mitangibst wird einmal in setOwner addModel aufgerufen
und explizit in deinem Code...
Daher wahrscheinlich die doppelte Größe.Was mir sonst auffällt:
Model(Unit *o = NULL) { owner_u = owner_u; // Die Zuweisung bewirkt gar nix... }Außerdem rufst du den Konstruktor der Basis-Klasse immer mit NULL auf, da der
parameterlose Konstruktor gewählt wird, wenn kein anderer angegeben ist.Gruß,
CSpille
-
CSpille schrieb:
Was mir sonst auffällt:
Model(Unit *o = NULL) { owner_u = owner_u; // Die Zuweisung bewirkt gar nix... }Diese Zuweisung bewirkt einerseits erstmal gar nichts, andererseits führt sie dann aber auch dazu, dass owner_u de facto uninitialisiert ist, da es erst einen nicht definierten (sprich zufälligen) Wert erhält und diiesen dann wieder an sich selbst zuweist. Eigentlich muss es also owner_u = o; heißen;
Außerdem (was allerdings kein wirklicher Fehler ist) solltest du dir die Semikolons hinter den Methodendefinitionen, also zum Beispiel hier:
void inline sSet(bool s) {set = s;}; //Das letzte Semikolon braucht man nchteinfach weglassen, sie sind überflüssig und verwirren nur...
Felix
-
die semikolons sind wirklich etwas überflüssig und ich habe sie nur weitergeführt weil ein bekannter diese klasse so angefangen hatte... das macht man das aus gewohnheit.
diese zuweisung ist in der tat sinnlos, ich habe wohl in der eile einen copyfehler gemacht.
Model(Unit *o = NULL) { owner_u = owner_u; // Die Zuweisung bewirkt gar nix... }danke, ich habe jetzt den fehler, ich war wohl betriebsblind... THX. es war diese verdammte setOwner fkt... ich werde noch die NULL zuweisung verbessern, damits kein unvorhersehbares verhalten mehr gibt.