Komische Werte bei Methodenaufruf aus anderer Klasse
-
Verstehe nicht warum ich keine sauberen Werte bekomme...
edit: gelösst ...
myBaugrundsteuck.Grundstueck::setpreis(10);#include "Aufg18.h" int main() { Grundstueck myGrundsteuck("Graz",1,2,3); myGrundsteuck.setpreis(10); myGrundsteuck.zeigeGrunddaten(); // funktioniert Baugrundstueck myBaugrundsteuck("Hello",1,2,3,4,5); myBaugrundsteuck.setpreis(10); myBaugrundsteuck.zeigeHausdaten(); // komische Werte }output:
Gemarkung: Graz
Flur: 1
Flurstueck: 2
Groesse: 3
Wert: 540Baujahr des Hauses: 4
Wohnflaeche des Hauses: 5
Aufruf anderer Klassenmethode =1.68547e+009// bspl0050.h #ifndef _BAUGRUNDSTUECK_ #define _BAUGRUNDSTUECK_ #include "bspl0048a.h" class Baugrundstueck : public Grundstueck { public: Baugrundstueck(const char *n, int f, int st, int g,int a, int b); Baugrundstueck(); void setpreis(float preis); void speichereHausdaten(int a, int b); void zeigeHausdaten() const; float berechneVolumenpreis() const; private: int baujahr,groesse,preis; }; #endif // bspl0050.cpp #include <iostream> #include "bspl0050a.h" // Baugrundstueck.h using namespace std; void Baugrundstueck::speichereHausdaten(int a, int b) { baujahr=a; groesse=b; sachwert+=static_cast<float>(groesse)*2.7F*320; } Baugrundstueck::Baugrundstueck() { } void Baugrundstueck::setpreis(float preis) { this->preis = preis; } float Baugrundstueck::berechneVolumenpreis() const{ return Grundstueck::berechneFlaechenpreis() * preis; } Baugrundstueck::Baugrundstueck(const char *n, int f, int st, int g,int a, int b) : Grundstueck(n,f,st,g) { speichereHausdaten(a,b); } void Baugrundstueck::zeigeHausdaten() const { cout << "\n" << "Baujahr des Hauses: " << baujahr << "\n" << "Wohnflaeche des Hauses: " << groesse << "\n" << "Aufruf anderer Klassenmethode =" << Grundstueck::berechneFlaechenpreis(); }// Grundstueck.h (bspl0048.h) #ifndef _GRUNDSTUECK_ #define _GRUNDSTUECK_ class Grundstueck { public: Grundstueck(); ~Grundstueck(); Grundstueck(const char *n, int f, int st, int g); void speichereGrunddaten(const char *n, int f, int st, int g); void zeigeGrunddaten() const; void setpreis(float preis); float berechneFlaechenpreis() const; private: char gemarkung[30]; protected: int flur, flurstueck, groesse,preis; float sachwert; }; #endif // Grundstueck.cpp (bspl0048.cpp) #include <iostream> #include <cstring> #include "bspl0048a.h" // Grundstueck.h using namespace std; Grundstueck::Grundstueck() { } Grundstueck::Grundstueck(const char *n, int f, int st, int g) { speichereGrunddaten(n,f,st,g); } Grundstueck::~Grundstueck() { } void Grundstueck::setpreis(float preis) { this->preis = preis; } float Grundstueck::berechneFlaechenpreis() const{ return preis * groesse; } void Grundstueck::speichereGrunddaten(const char *n, int f, int st, int g) { strncpy(gemarkung, n, 29); flur=f; flurstueck=st; groesse=g; sachwert=static_cast<float>(g)*180; } void Grundstueck::zeigeGrunddaten() const { cout << "\n" << "Gemarkung: " << gemarkung << "\n" << "Flur: " << flur << "\n" << "Flurstueck: " << flurstueck << "\n" << "Groesse: " << groesse << "\n" << "Wert: " << sachwert << "\n"; //<< "Preis: " << berechneFlaechenpreis(); }// Aufg18.h #ifndef _BAUDENKMAL_ #define _BAUDENKMAL_ #include "bspl0050a.h" class Baudenkmal : public Baugrundstueck { public: Baudenkmal(); Baudenkmal(char *z,int a, int b,const char *n, int f, int st, int g); void speichereGebaeudeteil(char *z); void zeigeGebaeudeteil() const; private: char schutz[51]; }; #endif // Aufg18.cpp #include <cString> #include <iostream> #include "Aufg18.h" using namespace std; void Baudenkmal::speichereGebaeudeteil(char *z) { strncpy(schutz, z, 50); } Baudenkmal::Baudenkmal() { } Baudenkmal::Baudenkmal(char *z,int a, int b,const char *n, int f, int st, int g) : Baugrundstueck(n,f,st,g,a,b){ speichereGebaeudeteil(z); } void Baudenkmal::zeigeGebaeudeteil() const { cout << "\n" << "Geschuetztes Gebaeudeteil: " << schutz; }
-
Der Default-Ctor von Grundstueck initialisiert nix.
Und die Member
Grundstueck::preisundBaugrundstueck::preissind zwei verschiedene Variablen, genau soGrundstueck::groesseundBaugrundstueck::groesse.Grundstueck::preisundGrundstueck::groessewerden also nirgends initialisiert.Grundstueck::berechneFlaechenpreisgreift also auf nicht-initialisierte Variablen zu.=> Nochmal Grundlagen büffeln.
-
Daran büffele ich gerade und ich tue mich sehr schwer.. ... bei virtuelle Methoden bin ich noch nicht. Die mal außen vor.
Wir haben 3 Klassen.
Klasse 1 mit 1 int Member variablen
Klasse 2 mit 1 int Member variablen
Klasse 3 mit 1 int Member variablenKlasse 3 erbt von Klasse 2 und die erbt von 1
dann glaube ich schaut es variablen technisch so aus.
Klasse 1 besitzt eine int Variable
Klasse 2 besitzt zwei int Variablen
Klasse 3 besitzt drei int Variablen die alle unterschiedliche Werte haben können.Eine Variable die den gleichen Namen hat ist drei mal gleichzeitig vorhanden. Ist das nicht vollkommen schwer zu durchblicken... vor allem wenn es dann komplexer wird ?
-
Bullz schrieb:
Wir haben 3 Klassen.
Klasse 1 mit 1 int Member variablen
Klasse 2 mit 1 int Member variablen
Klasse 3 mit 1 int Member variablenKlasse 3 erbt von Klasse 2 und die erbt von 1
dann glaube ich schaut es variablen technisch so aus.
Klasse 1 besitzt eine int Variable
Klasse 2 besitzt zwei int Variablen
Klasse 3 besitzt drei int Variablen die alle unterschiedliche Werte haben können.Korrekt
Eine Variable die den gleichen Namen hat ist drei mal gleichzeitig vorhanden. Ist das nicht vollkommen schwer zu durchblicken... vor allem wenn es dann komplexer wird ?
Möglich. Aber dieser Fall tritt eigentlich erst dann auf, wenn mit der Klassenhierarchie etwas nicht stimmt. Wieso sollten die denn alle den gleichen Namen haben, wenn ihre Klassen jeweils etwas unterschiedliches modellieren?
-
SeppJ schrieb:
Bullz schrieb:
Korrekt
Eine Variable die den gleichen Namen hat ist drei mal gleichzeitig vorhanden. Ist das nicht vollkommen schwer zu durchblicken... vor allem wenn es dann komplexer wird ?
Möglich. Aber dieser Fall tritt eigentlich erst dann auf, wenn mit der Klassenhierarchie etwas nicht stimmt. Wieso sollten die denn alle den gleichen Namen haben, wenn ihre Klassen jeweils etwas unterschiedliches modellieren?
Ich habe das anderes gemeint. In meinem Beispiel hätten ich 3 Klassen und wenn die Elternklasse eine Variable hat dann haben sie auch alle ihre Kinder. Das hat nichts damit zu tun ob ich meine Variablen in der anderen Klasse anderes benenne .. das kann und werde ich tun

aber das int a aus Klasse1 auch als int a in Klasse 2 und 3 vorhanden ist. Das habe ich gemeint...
Ich behelfe mir folgend ... zu fragen wie hoch a ist ist falsch. Die Frage ist wie der Wert a für die Klasse 1,2,3 ist ... sowas kannte ich von C nicht ... damit komm ich halbwegs klar.
-
(public) Vererbung ist eine "ist ein"-Beziehung.
class A; class B : public A;heißt B ist ein A. Da ein B also ein A ist, hat es auch sämtlich Eigenschaften eines A. Es kann natürlich auch noch weitere Eigenschaften haben, die alle Bs haben, aber nicht unbedingt jedes A haben muss.
-
Wenn B von A erbt, dann würde man das in C ca. so abbilden:
struct A { ... }; struct B { struct A base; ... };Wenn du dann schreibst...
struct A { int x; }; struct B { struct A base; int x; };Dann gibt es ja auch zwei x in B, eines von B selbst und eines in "base" drinnen.
Ist doch alles ganz logisch.
In C++ ist es nix anderes.Und real ist daran gar nix kompliziert. Es wäre dagegen ganz ganz schlimm wenn die Sprache Membervariablen mit dem selben Namen zu einer einzigen Variable zusammenfassen würde. Dann könnte man nämlich ganz schnell, ohne es zu wollen, die Funktion einer Basisklasse kaputtmachen können.
Und real wird auch viel weniger abgeleitet als man meinen könnte wenn man eine OO Sprache lernt. Klar, vererbung muss durchgenommen werden, weil man sie doch hin und wieder mal braucht. Speziell in C++ wo es keine Interfaces gibt. Aber man braucht sie viel viel seltener als die meisten Lernenden annehmen. Und wenn man sie braucht, dann meist ohne protected Datenmember. Und dann stellt sich die Frage gar nicht was die Basisklasse für Variablen haben könnte. Sie hat halt das was sie braucht, was auch immer das sein mag.