Vererbung (Fehlermeldung)
-
Moin moin,
ich versuche eine Klasse CSpieler von der Klasse CCharacter erben zu lassen.
Wenn ich es kompilieren will bekomme ich folgende Fehlermeldung:
In constructor CSpieler::CSpieler():
error: no matching function for call to CCharacter::CCharacter()
note: candidates are: CCharacter::CCharacter(std::string)
note: CCharacter::CCharacter(const CCharacter&)Hier der Quelltext:
CSpieler.h
#ifndef CSPIELER_H #define CSPIELER_H #include "CCharacter.h" /* * *** Erbt von CCharacter *** * */ class CSpieler : public CCharacter { public: // Membervariablen // Membermethoden CSpieler(); virtual ~CSpieler(); }; #endif // CSPIELER_HCSpieler.cpp
#include "CSpieler.h" #include "CCharacter.h" #include <string.h> #include <iostream> using namespace std; CSpieler::CSpieler() { } CSpieler::~CSpieler() { //dtor }CCharacter.h
#ifndef CCHARACTER_H #define CCHARACTER_H #include <string.h> #include <iostream> using namespace std; class CCharacter { protected: // Membervariablen string m_Name; // Name des Charakters int m_HealthyPoints; // Energie (HP) public: // Membermethoden CCharacter(string name); // Erweiterter Konstruktor für Namenseingabe virtual ~CCharacter(); // Std. Destruktor void setName(string name); void setHealthyPoints(); string getName(); int getHealthyPoints(); void print(); }; #endif // CCHARACTER_HCCharacter.cpp
#include "CCharacter.h" #include <iostream> #include <string.h> using namespace std; CCharacter::CCharacter(string name) { // Standart-Werte initialisieren setName(name); setHealthyPoints(); } void CCharacter::setName(string name) { m_Name = name; } string CCharacter::getName() { return m_Name; } void CCharacter::setHealthyPoints() { m_HealthyPoints = 400; } int CCharacter::getHealthyPoints() { return m_HealthyPoints; } void CCharacter::print() { cout << "Name: " << m_Name << endl; cout << "HP: " << m_HealthyPoints << endl; }habs auch schon versucht mit CSpieler::CSpieler() : CCharacter
aber das hat auch nicht viel gebracht^^Über Tipps wär ich sehr dankbar^^ Komme hier grade echt nicht weiter, weil ich auch irgendwie nicht verstehe was falsch sein soll... Hatte eigendlich nie Probleme bis ich versucht hab die Quellcodes in Header und Cpp Dateien aufzusplitten^^

-
Du erbst von CCharacter. Die abgeleitete Klasse muss in ihrem ctor/vor ihrem ctor-Aufruf den ctor von CCharacter aufrufen. Normalerweise würde der default-ctor verwendet. Da Du aber in CCharacter einen neue ctor definiert hast, fällt der default-ctor weg. Übrig bleibt nur Dein ctor mit Argument string. Das Kann der Compiler aber nicht selbst aufrufen.
Lösungen:
- CCharacter einen Standard-ctor (:= ohne Argumente) verpassen
- Den CCharacter-ctors im ctor der abgeleiteten Klasse aufrufen
-
Die Idee der Klasse CCharacter einen STd. Konstruktor zu geben hatte ich auch shcon. Nur dann bekomme ich gleich 10 Errormeldungen^^
-> undefined reference to 'vtable for CCharacter'
-> undefined reference to 'CCharacter::~CCharacter()'und das ganze dann halt 10 mal...
Ausser ich verstehe das mit dem Std. Konstruktor falsch^^ Habe der Klasse CCharacter einfach jetzt die Zeilen:
CCharacter();hinzugefügt
In der Cpp
CCharacter::CCharacter() { }
-
nein du musst in der CSpielerklasse per initailisierungsliste den konstruktor von CCharacter aufrufen
CSpieler::CSpieler() : CCharacter("lol") { // ... }
-
Das liegt daran, dass du angibst, dass du einen eigenen Destruktor hast, diesen aber nirgends definierst.
-
Nach dem löschen des Destruktors ging es

Alles klar Problem ist damit gelöst, danke für die Antworten

-
Obwohl ein Problem gibt es doch noch zum Thema Vererbung.
Klasse main.cpp
CSpieler spieler(); spieler.print(); return 0;Durch die Vererbung sollte es doch jetzt möglich sein, die print()-Methode aus der Klasse CCharacter aufzurufen
Nur leider schmeisst mein Compiler hier ein Fehler:-> error: request for member print in spieler which is of non-class type CSPieler()
Muss ich die print Methode jetzt überschreiben? Dann hätte doch die Vererbung hier garkeinen Sinn^^ Da ich ja (bis jetzt zumindest) noch keine anderen EIgenschaften habe die ich ausgeben möchte?
-
CSpieler spieler();Das ist eine Funktionsdeklaration.
-
Mh ja stimmt aber selbst wenn ich es so mache, meldet mein compiler den selben Fehler:
CCharacter *pSpieler; pSpieler = new CSpieler; pSpieler.print(); return 0;
-
Bestimmt nicht den selben, aber einen ähnlichen. Hier hast du kein Objekt, sondern einen Zeiger, den du erstmal dereferenzieren mußt (per
(*pSpieler).print();oderpSpieler->print();).Aber was hindert dich daran, einfach eine lokale Variable anzulegen?
CSpieler spieler; spieler.print(); return 0;
-
Nichts oO
lol Ja doch jetzt geht es mitCSpieler spieler;
spieler.print();Hab wohl zu lange mit Java programmert ohne was mit Cpp zwischendurch zu machen xD
Denn ich muss bzw. kann ja auch CCharacter so initialisieren:CCharacter character("Name"); character.print();Nun dacht ich, wenn ich ein Objekt erzeuge ohne Patrameter muss zumindest die leere Angabe dabeistehen:
CCharacter character(); ...Bin es nämlich so gewohnt (von Java her):
CCharacter character = new CCharacter();
-
Und wenn Du new benutzt, ist das auch in Ordnung. Wenn Du es nicht benutzt, aber eben nicht.
-
So. Hoffe das ist jetzt alles so richtig^^ Wollte nur nochmal fragen ob das so "richtiger" Code ist^^ bzw. ob man das auch wirklich so schreiben würde^^ Gibt ja immer schönen und nicht so schönen Code^^
CCharacter.h:
// Konstruktoren CCharacter(); CCharacter(string name);CSpieler.h, erbt von CCharacter
CSpieler(); CSpieler(string name)CCharacter.cpp
CCharacter::CCharacter() {} CCharacter::CCharacter(string name) { setName(name); set... }CSpieler.cpp
CSpieler::CSpieler() {} CSpieler::CSpieler(string name) : CCharacter(name) { }Brauche ich die leeren (standart?) Konstruktoren jetzt überhaupt?^^ Oder kann ich die auch einfach weg lassen?

-
Prinzipiell ist es deine Entscheidung, ob du einen namenlosen Charakter bzw. Spieler zulassen willst. Wenn du sicher gehen willst, daß neue Figuren nur mit Name erzeugt werden können, lässt du sie weg.