Herzlich Willkommen, lieber Gast!
  Sie befinden sich hier:

  Forum » C / C++ (ANSI-Standard) » Neulingsfrage: OO-Klassenkonzept

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 <
000
17.10.2006, 01:43 Uhr
~derMond
Gast


Hallo,
ich habe eine klasse die einen eigenen stl container benutz ca so:
ob die klasse sinn macht oder nicht ist jetzt egal - mir gehts ums verständnis der
nutzung wo ich im moment probleme habe...

C++:
#include ...
class MyClass
{

     public:
        map<int, myStruct> myMap;

         MyClass();
         ~MyClass();

         void My_Insert_Function(...);

    private:
};



in einer anderen klasse will ich jetzt die method find die die stl::map bereitstellt auf meiner map nutzen. Ist das folgende so korrekt? Also funktionieren tuts aber ich bin mir unsicher ob das so auch gemacht wird:


C++:

...
MyClass mc;
mc.My_Insert_Function(...);

std::map<...>::iterator it;

//Hier kommt das wichtige..
//ist es so gewöhnlich über den member der
//Klasse MyClass zu fragen?
it = mc.myMap.find(...);

//Ich hätte eher sowas erwartet:
it = mc.find(...);

...




was ist denn so am üblichsten....

Danke
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
001
17.10.2006, 08:55 Uhr
virtual
Sexiest Bit alive
(Operator)


Es ist eher unüblich, Instanzattribute public zu machen; stattdessen greift man üblicherweise über entsprechende get/set Methoden darauf zu:

C++:
class MyClass {

private:
        map<int, myStruct> myMap;

public:
        map<int,myStruct>& getMyMap() { return myMap; }
};


Aber selbst das ist noch nicht der weisheit letzter Schluß: die obige Variant gibt eine veränderbare Map zurück. Dh wenn man es wie oben sieht, dann kann Derjenige, welcher die map bekommt, machen mit hier, was er will. Der Gedenke sollte aber in der Regel sein, daß der Eigentümer der Map, als das Objekt von MyClass die alleinige Schreib Zugriffe hat. Daher sollte der getter Readonly sein:

C++:
class MyClass {

private:
        map<int, myStruct> myMap;

public:
        const map<int,myStruct>& getMyMap() const { return myMap; }
};


Anwenden kannst Du das dann so:

C++:
mc.getMyMap().find(...)


--
Gruß, virtual
Quote of the Month
Ich eß' nur was ein Gesicht hat (Creme 21)
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
002
17.10.2006, 11:00 Uhr
J-jayz-Z
Perl Crack ala Carte
(Operator)



Zitat von virtual:
Es ist eher unüblich, Instanzattribute public zu machen; stattdessen greift man üblicherweise über entsprechende get/set Methoden darauf zu

Das stimmt so zwar in C++ aber in anderen Sprachenn wie C# beispielsweise ist es durchaus üblich öffentliche Variablen zu benutzen - vor allem um Informationen zu einem Objekt zu bekommen. Manchmal kann das durchaus von Vorteil sein.

EDIT: Die Sprache ist auch eher dafür ausgelegt, da es Listener gibt, die bei Änderung dieser Variablen Methoden ausführen. Ich denke da wollte sich Microsoft etwas von anderen Sprachen abheben.
--
perl -Mstrict -Mwarnings -e 'package blub; sub new { bless {} } sub bar {my $self=shift; $self->{bla}="66756e2d736f66742e6465"; return $self->{bla};} my $foo=blub->new();print "Hallo ";print pack("H*",$foo->bar()); print "\n"'

Dieser Post wurde am 17.10.2006 um 11:02 Uhr von J-jayz-Z editiert.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
003
17.10.2006, 11:55 Uhr
RHBaum




Zitat:

Das stimmt so zwar in C++ aber in anderen Sprachen


Kapselung ist ein wichtiger Eckstein der OO ... also sollte das eigentlich fuer alle Objektorientierten Sprachen gelten. Die frage ist eigentlich nur, was der "compiler/interpreter" im hintergrund generiert (wenn man z.b. so eigenschaften im windows/com programmierstiel implementiert) und ob das noch sinnvoll ist (ob man die getter und setter anpassen kann, wenn nen setter und getter nur die member stupide nach aussen gibt und keine möglichkeit gibt die zu veraendern, sind sie ja quasi witzlos ^^)

Da man bei c++ auf relativ niederer ebene rangiert, gibts sowas nicht und man darf alles per hand machen oder benutzt code generatoren , Gott sei dank ^^


@derMond


Zitat:

//Ich hätte eher sowas erwartet:
it = mc.find(...);


wenn du sowas willst, braucht deine klasse "eigene" iteratoren ... oder muss iteratoren deiner Containerklasse nach aussen geben ^^ das geht natuerlich auch.
Dann solltest also alle iteratorfunktionen mit nach aussen geben ...
So kann man quasi eigene container auf stl container basis schreiben ...

C++:
class MyClass
{
public:
        typedef std::map<int, myStruct>::iterator Iter;
        typedef std::map<int, myStruct>::const_iterator ConstIter;

        Iter find(int v) { return myMap.find(v); }
        ConstIter find(int v) const { return myMap.find(v); }

        Iter begin() { return myMap.begin(); }
        ConstIter begin() const { return myMap.begin(); }

        Iter end() { return myMap.end(); }
        ConstIter end() const { return end.begin(); }
private:
        std::map<int, myStruct> myMap;

};



nu kannst auf deiner klasse rumrutschen wie auf ner stl klasse ....


C++:
MyClass::ConstIter it = mc.find(5);
if(it != mc.end())
{
         // Tu was
}



P.S.
Du verwendest stl klassen in nem header, und schreibst den namespace nicht davor
- also verwendest du die (ver)alte(de)n header -> poese
- du benutzt using std in nem header -> mindestens genau so poese !

Ciao ...

Dieser Post wurde am 17.10.2006 um 11:57 Uhr von RHBaum editiert.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
004
17.10.2006, 12:59 Uhr
J-jayz-Z
Perl Crack ala Carte
(Operator)



Zitat von RHBaum:

Zitat:

Das stimmt so zwar in C++ aber in anderen Sprachen


Kapselung ist ein wichtiger Eckstein der OO ... also sollte das eigentlich fuer alle Objektorientierten Sprachen gelten. Die frage ist eigentlich nur, was der "compiler/interpreter" im hintergrund generiert (wenn man z.b. so eigenschaften im windows/com programmierstiel implementiert) und ob das noch sinnvoll ist (ob man die getter und setter anpassen kann, wenn nen setter und getter nur die member stupide nach aussen gibt und keine möglichkeit gibt die zu veraendern, sind sie ja quasi witzlos ^^)

Da man bei c++ auf relativ niederer ebene rangiert, gibts sowas nicht und man darf alles per hand machen oder benutzt code generatoren , Gott sei dank ^^

Es ist zwar schön, wenn man sich an bestimmte "Designvorschriften" hällt aber ich finde, es sollte jeder selbst für sich entscheiden, ob er öffentliche Variablen oder getter und setter verwendet. Machen tut es prinzipiell das selbe - ist nur unterschiedlich viel Schreibarbeit
--
perl -Mstrict -Mwarnings -e 'package blub; sub new { bless {} } sub bar {my $self=shift; $self->{bla}="66756e2d736f66742e6465"; return $self->{bla};} my $foo=blub->new();print "Hallo ";print pack("H*",$foo->bar()); print "\n"'
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
005
17.10.2006, 13:32 Uhr
RHBaum




Zitat:

Machen tut es prinzipiell das selbe - ist nur unterschiedlich viel Schreibarbeit


In dem falle eben nicht ....
Erweiterbarkeit, Anpassbarkeit ...

bei nem getter und setter kann ich immer noch was unterschieben, ne zusaetzliche umrechnung, nen Mutex fuer multithreading, ne verschluesselung ^^
Wenn ich getter und setter aufrufe, statt die variable direkt zu manipulieren ... hab ich quasi ne schnittstelle, mit etwas gescheiten design drumherum kann ich notfalls das komplette object austauschen, ohne das die beteiligten Objekte umgeschrieben werden muessen ....

Wenn man nur die Schreibarbeit sieht, sollte man die Finger von OO ganz lassen ^^ OO wird erst so richtig wirksam, wenn klassen eben wiederverwendet werden, teil einer biblo sind ... etc. Wenn ich 100% weiss das meine "klasse" nur einmal und genau an dieser stelle verwendet wird, und nie nie wieder angefasst werden muss ... dann pfeiff ich natuerlich auch auf die Grundlagen der OOP ! aber wer ist sich sschon 100% sicher :-)

Ciao ....

Dieser Post wurde am 17.10.2006 um 13:34 Uhr von RHBaum editiert.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
006
17.10.2006, 16:36 Uhr
virtual
Sexiest Bit alive
(Operator)



Zitat von J-jayz-Z:

Es ist zwar schön, wenn man sich an bestimmte "Designvorschriften" hällt aber ich finde, es sollte jeder selbst für sich entscheiden, ob er öffentliche Variablen oder getter und setter verwendet. Machen tut es prinzipiell das selbe - ist nur unterschiedlich viel Schreibarbeit


Natürlich muß man das für sich selbst entscheiden, aber es gibt auch gute Gründe dafür, daß man sich an die Designvorschriften halten sollte. Mal ein kleines Beispiel:

C++:
class NamedObject {
public:
     std::string name;
public:
     NamedObject(const std::string& name) :name(name) { }
};


Nehmen wir mal an, wir haben diese Klasse als Klasse für allerlei Benamte Objekte. Nehmen wir weiterhin an, daß Programm, welches diese Klasse benutzt ist in der Version 1.0 released und total Fehlerfrei. Die Klasse mag jetzt an 1000 Stellen benutzt werden, wo der Name verändert wird.

Aus welchen Gründen auch immer entscheidet man sich nun, eine Version 1.1 rauszubringen, die nur eine ganz kleine Änderung hat, die man beim Ursprünglichen Design einfach "übersehen" hat: es soll nicht möglich sein, leere Namen einzugeben. Ohne Setter bist Du aufgeschmissen.

Es mag sein, daß man für bestimmte Attribute (zB X/Y Koordinaten einer allgemeinen Klasse Punkt2D) keine Getter schreiben will. Aber sobald zB diese eigentlich trivial Klasse zB Ableitbar ist und man eine Klasse Punk2DAufLinie hat, so daß an das Verhältnis von X zu Y irgendwelchen Restruktionen unterworfen ist, sind zumindestens schon mal setter angesagt.

Damit ist aus meiner Sicht schonmal für jede Ableitbare Klasse pflicht, setter zu verwenden.
(Natürlich nicht für Attribute die const sind oder - in Java - final sind).

Blieben also nur noch Klassen übrig die nicht ableitbar sind. Das ist in C++ in der Regel ein erheblich größerer Anteil als in anderen Sprachen. Aus dem Beispiel oben motiviert würde ich mal da die Einschränkung machen, daß wenn man sich vorstellen kann, daß man sich die setter für Properties sparen kann, wenn man die Klasse 100% niemals verwendet (dann schreibe ich sie nicht!) oder verändert. Dies ist bei mir eigentlich nur bei "Wegwerfprogrammen" der Fall, die irgendwo im tmp Ordner liegen und nach 2 Tagen von irgendeinem Cronjob automatische gelöschgt werden.

In C# kenne ich mich nicht so aus, aber ich denke mal daß grade dieses ListenerKonzept für Properties was Du angesprochen hast im wesentlichen genau wie ein normaler Setter wirkt, eben indem man in einem Listener prüft, ob alle Bedingungen erfüllt sind, die notwendig sind, den Wert zu setzen. Aber leider reden wir hier von C++, nicht C#.
--
Gruß, virtual
Quote of the Month
Ich eß' nur was ein Gesicht hat (Creme 21)

Dieser Post wurde am 17.10.2006 um 16:38 Uhr von virtual editiert.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
007
17.10.2006, 17:03 Uhr
Guybrush Threepwood
Gefürchteter Pirat
(Operator)


In C# ist es eigentlich auch üblich mit Gettern und Settern zu arbeiten...
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
008
17.10.2006, 23:22 Uhr
~derMond
Gast


Hallo,
danke für die Antworten - ich verstehe es jetzt ein wenig mehr ja. Aber ich habe probleme mit den const's in dem beispiel von virtual. Ich habe das beispiel nun so:


C++:
#include ...
class MyClass
{

     public:
        
         MyClass();
         ~MyClass();

         void My_Insert_Function(...);
         const std::map<...>& Get_Map() const {return myMap;}

    private:
          map<...> myMap;
};

..
MyClass mc;
mc.My_Insert_Function(...);

std::map<...>::iterator it;

//hier schreit er - nur ohne const geht das folgende mit aber nicht
it = mc.Get_Map().find(...);




Irgendwie haut das mit dem const noch nicht so ganz hin...warum verstehe ich aber nicht denn ich verändere mit dem find ja nix...

danke für hilfe
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
009
17.10.2006, 23:24 Uhr
~derMond
Gast


Aaaargh - dass ich immer direkt nachm posten drauf komm....hab den iterator natürlich vergessen auf ::const_iterator zu setzen ....sorry
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
Seiten: > 1 <     [ 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: