Herzlich Willkommen, lieber Gast!
  Sie befinden sich hier:

  Forum » C / C++ (ANSI-Standard) » objekt im vector bestimmen

Forum | Hilfe | Team | Links | Impressum | > Suche < | Mitglieder | Registrieren | Einloggen
  Quicklinks: MSDN-Online || STL || clib Reference Grundlagen || Literatur || E-Books || Zubehör || > F.A.Q. < || Downloads   

Autor Thread - Seiten: > 1 < [ 2 ]
000
06.09.2004, 14:44 Uhr
~Dani
Gast


Und wieder mal haben wir ein Problem mit einem Vector.

Wir haben einen vector vom typ Medium, da stehen Objekte unterschiedlicher Unterklassen drin. ALso zB CdAudio, Tape, Vinyl.

Wenn wir jetzt den Typ des Objektes an einer bestimmten Stelle im Vector feststellen wollen, scheitern wir jedes Mal.

Als erstes haben wir es mit typeid versucht, aber das hat nicht geklappt. Jetzt sind wir auf die Idee gekommen, den Unterklassen noch einen String hinzuzufügen, indem der Objekttyp steht.

In Medium.cpp ist die Methode string getType und void setType leer und in medium.h sind die beiden MEthoden virtual gesetzt.

In den Unterklassen sind die Methoden auch virtual, heißen ebenfalls string getType und void setType und dort wird beim konstruieren des Objekts der Name gesetzt.

Wenn wir jetzt aber


C++:
mainVec[i].getType();


aufrufen, wird immer in die getType Methode von Medium verzweigt und nicht in die Richtige Unterklasse.

Woran liegt das???
Kann es sein dass im Gegensatz zum Array, in einem Vector die Datentypen verloren gehen???
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
001
06.09.2004, 14:51 Uhr
Oliver
S2-Pixelgeneral


Hmm, ich hoffe, ich habe dich jetzt richtig verstanden, ich würde den Typ in eine Membervariable schreiben und dann einfach nur eine Funktion GetType definieren und die dann in der Basisklasse definieren und nicht virtual.
--
Demokratie ist die Diktatur der Mehrheit.

www.siedler25.org/ ( Siedler2 - Remake )
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
002
06.09.2004, 14:58 Uhr
~Dani
Gast


Sorry falls das ne doofe Frage ist, aber was ist eine Membervariable ?

Hast du da evtl n Beispiel dafür???
Ich denke nämlich shcon dass du mich richtig verstanden hast...
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
003
06.09.2004, 15:03 Uhr
~Dani
Gast


Ahhh, ich glaube ich weiß schon was du meinst.
Du meinst, man sollte type nur als Attribut der Oberklasse deklarieren und in den Unterklassen gar nicht erwähnen und somit den getter und setter auch nur in die Oberklasse schreiben!?
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
004
06.09.2004, 15:03 Uhr
Airdamn




C++:
int nAndereZahl // keine Membervariable

class CMyClass
{
int m_nZahl; // Membervariable von CMyClass
}


Dieser Post wurde am 06.09.2004 um 15:04 Uhr von Airdamn editiert.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
005
06.09.2004, 15:08 Uhr
Oliver
S2-Pixelgeneral


Na damit meine ich eine ganz normale Variable, die du in deiner Klassw deklarierst, also etwa so und dann noch eine Funktion dazu, wo du sie abfragst:


C++:
class Basis
{

string member_id;

public:

string GetId();
};

string Basis:GetId()
{
return member_id;
}



Dann musst du nur noch im Konstruktur, der Klassen, die von Basis abgeleitet werden im Konstruktor schreiben, member_id="Klasse1". also den Bezeichner.
--
Demokratie ist die Diktatur der Mehrheit.

www.siedler25.org/ ( Siedler2 - Remake )
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
006
06.09.2004, 15:09 Uhr
Oliver
S2-Pixelgeneral



Zitat von ~Dani:
Ahhh, ich glaube ich weiß schon was du meinst.
Du meinst, man sollte type nur als Attribut der Oberklasse deklarieren und in den Unterklassen gar nicht erwähnen und somit den getter und setter auch nur in die Oberklasse schreiben!?


Ja, so mein ichs
--
Demokratie ist die Diktatur der Mehrheit.

www.siedler25.org/ ( Siedler2 - Remake )
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
007
06.09.2004, 15:16 Uhr
~Dani
Gast


jo, das ist mal ne idee! tausend dank, ich hoffe das klappt jetzt !
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
008
06.09.2004, 15:18 Uhr
virtual
Sexiest Bit alive
(Operator)



Zitat von ~Dani:
Und wieder mal haben wir ein Problem mit einem Vector.

Wir haben einen vector vom typ Medium, da stehen Objekte unterschiedlicher Unterklassen drin. ALso zB CdAudio, Tape, Vinyl.

[...]

Wenn wir jetzt aber


C++:
mainVec[i].getType();


aufrufen, wird immer in die getType Methode von Medium verzweigt und nicht in die Richtige Unterklasse.

Woran liegt das???
Kann es sein dass im Gegensatz zum Array, in einem Vector die Datentypen verloren gehen???


Ja, aber nicht im Unterschied zu einem Array:
wenn Du etwas in einen vektor reinschreibst, wird nicht etwa das Original reingetan, sondern eine Kopie. Die Kopie wird dabei durch den Aufruf vom Copy constructor von Medium gemacht, weil Du eben einen std::vector<Medium> hast. Die Informationen, die zusätzlich in einem CTape oder was auch immer stehen, gehen unweigerlich verloren.

Das hat auch einen Grund: Nimm einfach mal der einfachheit halber an, daß ein Vecotr intern ein Array ist. (Dem ist idR tatsächlich so). Ein Array zeichnet sich dadurch aus, daß alle Elemente den gleichen Typen haben. Also Medium. Erst diese Gleichheit macht es überhaupt möglich, daß man schnell auf die Elemente zugreifen kann. Denn in der Regel werden Spezielisierungen von Medium Felder an die Medium Klasse hinzufügen und damit ein Objekt größer machen. Wären die Felder nicht gleich groß, müsste zB beim Zugriff auf das 100ste Feld zunächst zusammengerechnet werden, wie groß die Felder 1 - 99 sind, um überhaupt herauszufinden, wo das 100ste Objekt anfängt.

Einen Ausweg gibt es auch: man tut in den Vektor nur noch Pointer:

C++:
std::vector<Medium*> mainVec;
...
mainVec.push_back(new CTape(...));
mainVec.push_back(new CVideo(...));
...
mainVec[0]->getType(); .



Problematisch ist hier, daß man nun selbst die Elemente freigeben muß, mit delete, weil man ja mit new gearbeitet hat. Aber auch dies kann man durch die Verwendung von Smart Pointern vermeiden:

C++:
std::vector< smart_ptr<Medium> > mainVec;
...
mainVec.push_back(new CTape(...));
mainVec.push_back(new CVideo(...));
...
mainVec[0]->getType(); .



--
Gruß, virtual
Quote of the Month
Ich eß' nur was ein Gesicht hat (Creme 21)

Dieser Post wurde am 06.09.2004 um 15:20 Uhr von virtual editiert.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
009
06.09.2004, 16:45 Uhr
(un)wissender
Niveauwart


Dann funktioniert nämlich auch typeid.
--
Wer früher stirbt ist länger tot.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
Seiten: > 1 < [ 2 ]     [ C / C++ (ANSI-Standard) ]  


ThWBoard 2.73 FloSoft-Edition
© by Paul Baecher & Felix Gonschorek (www.thwboard.de)

Anpassungen des Forums
© by Flo-Soft (www.flo-soft.de)

Sie sind Besucher: