const member und operator=
-
Sorry, der Beitrag bezog sich auf GPC. Da war ich wohl beim schreiben zu langsam
-
Hmm, bei mir klappt das nicht. Allerdings auch mit nem struct. liegt's daran? Ich muss wohl mal ein größeres Beispiel geben:
typedef struct _CurvatureInfo { const float MinPrincipalCurvature; _CurvatureInfo(const float minPrincipalCurvature = 0.0f) : MinPrincipalCurvature(minPrincipalCurvature) { }; }CurvatureInfo; // ... class CUtils { public: inline static CurvatureInfo CreateCurvature(/* some parameters */) { // some calculations return CurvatureInfo(calculatedValue); }; }; // .... // SomeClass.cpp void SomeClass::method() { //... CurvatureInfo* curvatures = new CurvatureInfo[num]; for(int i = 0; i < num; i++) { curvatures[i] = CUtils::CreateCurvature(/* the parameters */); } }Puh. Und in der for-Schleife mault der Compiler. Ich hoffe, der Code ist schlüssig. Habe ihn ziemlich zusammengestutzt.
-
Also entweder du setzt dein Attribut als Pseudo-Konstante (d.h. du sorgst dafür, daß niemand bewußt den Wert ändert) oder du lebst damit, die Objekte nicht zuweisen zu können (es macht ja auch wenig Sinn, einen existierenden Menschen zu überschrieben - und genau das wäre die Semantik hinter dem op=) und reichst nur Zeiger auf deine Objekte herum.
Edit: Und bei deinem Code-Beispiel wäre es eine gute Idee, STL-Container zu verwenden (und per push_back() mit Werten zu füllen).
-
FelixManke schrieb:
Jaja, aber wie kann ich denn eine Membervariable einführen, die sich nach Erzeugung NIE mehr ändert? Die z.B. von der Konstellation der im Konstruktor übergebenen Parameter abhängt?
Mit const ändert sich nie was.
Um auf dein Beispiel zu verweisen:
class Person { public: enum Geschlecht {M, W}; private: const Geschlecht g; //Keine Zuweisungen möglich Person& operator=(const Person&); public: Person(Geschlecht g_) : g(g_) {} // Ctor Person(const Person &p) : g(p.g) {} //Copy Ctor ~Person(); //Dtor Geschlecht getGeschlecht() const { return g; } }; //... Person me(Person::M); //Männlich Person you(me); //ebenfalls männlich, über Copy Ctor Person x(Person::W); you = x; //nix da, op= gesperrt, Geschlechtsumwandlungen sind böse.Klaro?

MfG
GPC
-
Du kannst durchaus auch const member haben. Du musst sie nur zum richtigen Zeitpunkt (Konstruktor) initialisieren:
CPerson.h:
#include <string> class CPerson { private: const int m_geschlecht; std::string m_name; public: CPerson(int Geschlecht, std::string Name); int getGeschlecht(); std::string &getName(); };CPerson.cpp:
#include "CPerson.h" CPerson::CPerson(int Geschlecht, std::string Name): m_geschlecht(Geschlecht), m_name(Name) { // All in initalizers } int CPerson::getGeschlecht() { return m_geschlecht; } std::string &CPerson::getName() { return m_name; }Main.cpp:
#include "CPerson.h" #include <iostream> int main(int argc, char **argv) { int dummy = 0; CPerson Sohn(1, "Peter"); CPerson Tocher(0, "Marianne"); std::cout << "Sohn Name: " << Sohn.getName() << " Geschlecht: " << Sohn.getGeschlecht() << std::endl; std::cout << "Tocher Name: " << Tocher.getName() << " Geschlecht: " << Tocher.getGeschlecht() << std::endl; std::cin >> dummy; }
-
Hmm, aber wie mache ich das in meinem konkreten Fall? Ich kann da ja schlecht einen Copy-Konstruktor benutzen, wenn ich das Ergebnis einfach von einer Methode entgegennehme. Und nen anderen Konstruktor kann ich auch nicht aufrufen.
-
Noch mal zur genaueren Erklärung:
curvatures[i] = CUtils::CreateCurvature(/* the parameters */);Hier wird intern der Zuweisungsoperator (=) deiner Klasse aufgerufen.
Da diese aber ein konstantes Member enthält, kannst du diesen Operator ja nicht verwenden (und der Compiler erzeugt auch keine Default-Implementation hierfür).Wenn du wirklich diese konstante Member behalten willst, mußt du mit Zeigern arbeiten, d.h. z.B.
inline static CurvatureInfo* CreateCurvature(/* some parameters */) { // some calculations return new CurvatureInfo(calculatedValue); // <-- hier new verwenden }; CurvatureInfo** curvatures = new CurvatureInfo*[num]; for(int i = 0; i < num; i++) { curvatures[i] = CUtils::CreateCurvature(/* the parameters */); }Und beim Zerstören des Arrays, dann
for(int i = 0; i < num; i++) { delete curvatures[i]; } delete [] curvatures;
-
Ok, Danke. Aber wenn Pointer und Heap die einzige Möglichkeit sind, lasse ich das const vielleicht einfach weg -- macht die Sache einfacher :-).
-
FelixManke schrieb:
Hmm, aber wie mache ich das in meinem konkreten Fall? Ich kann da ja schlecht einen Copy-Konstruktor benutzen, wenn ich das Ergebnis einfach von einer Methode entgegennehme. Und nen anderen Konstruktor kann ich auch nicht aufrufen.
Natürlich kannst du:
class Person { //wie oben }; Person foo() { Person p(Person::M); return p; } Person x = foo();Klappt doch

MfG
GPC
-
Das ist doch, sofern ich richtig schaue, derselbe Code, wie in meinem echten Beispiel mit der Curvature.
Ne Klasse (Person bzw. CurvatureInfo) mit nem const Member,
nen Konstruktor, wo dieser Member initialisiert wird,
ne Methode (einer anderen Klasse - foo() bzw. CUtils::CreateCurvature()), die ein neues Objekt erzeugt und
ne (lokale) Variable (einer dritten Klasse), die dieses Objekt empfängt (Person x bzw. curvatures[i]).Warum klappt das denn bei mir nicht?
-
FelixManke schrieb:
Das ist doch, sofern ich richtig schaue, derselbe Code, wie in meinem echten Beispiel mit der Curvature.
Keine Ahnung, hab deinen Code nicht gelesen.
Ne Klasse (Person bzw. CurvatureInfo) mit nem const Member,
nen Konstruktor, wo dieser Member initialisiert wird,nem Copy-Ctor und nem privat deklarierten op=.
Die Person x wird per Copy-Ctor mit dem Objekt, welches foo zurückgibt, initalisiert. Scharf, heh?

MfG
GPC
-
Oh sorry,
da habe ich vorhin nicht genau genug geguckt und das mit dem operator= übersehen
. Sorry.Scharf ist's wirklich. Wieso gibt sich denn der Compiler plötzlich damit zufrieden, wenn er GAR keinen Zuweisungsoperator mehr hat. Wie kommt der denn auf die Idee, plötzlich den Copy-Konstruktor zu nehmen?! Sonderbar....
-
Hallo GPC,
dein Beispiel entspricht aber nicht dem von FelixManke,
da du den Copy-Konstruktor bei "Person x = foo()" aufrufst, während
wie ich auch schon geschrieben habe, bei FelixManke's Programm der Zuweisungsoperator aufgerufen wird, d.h.Person x; x = foo();wird auch NICHT funktionieren!!!
-
Th schrieb:
Hallo GPC,
dein Beispiel entspricht aber nicht dem von FelixManke,
behauptete ich ja auch nicht

da du den Copy-Konstruktor bei "Person x = foo()" aufrufst, während
wie ich auch schon geschrieben habe, bei FelixManke's Programm der Zuweisungsoperator aufgerufen wird, d.h.Person x; x = foo();wird auch NICHT funktionieren!!!
korrekt...
FelixManke schrieb:
Scharf ist's wirklich. Wieso gibt sich denn der Compiler plötzlich damit zufrieden, wenn er GAR keinen Zuweisungsoperator mehr hat. Wie kommt der denn auf die Idee, plötzlich den Copy-Konstruktor zu nehmen?! Sonderbar....
...dazu folgendes Beispiel:
std::string s(""); //Ctor std::string s2(s); //Copy-Ctor std::string s3 = s; //Copy-Ctor, oha. std::string s4; s4 = s; //Zuweisungs operatorMfG
GPC