Virtuelle Funktion -



  • Hallo ­čÖé

    Ich versuche grade eine Klasse zu erstellen, die eine virtuelle Methode hat, die von klasse zu klasse unterschiedlich sein soll.

    Es geht um einen Komando Aufruf. Ein vector von <CMD_Interface> soll nach einem string durchsucht werden un bei Fund, die virtuelle Funktion m_method() ausf├╝hren, die je nach Komando anders ist.

    ich bekomme jetzt folgenden Fehler:

    error C2633: 'CMD_Interface': 'inline' ist die einzig zul├Ąssige Speicherklasse f├╝r Konstruktoren
    

    meine Klassen sehen so aus:

    class CMD_Interface				//cmd_interface.h
    {
    	public:
    		 CMD_Interface(string* command);
    		~CMD_Interface();
    
    		bool			execute_if_match(string* str);
    
    	private:
    		string			m_cmd;
    		virtual void	m_method(vector<string>* pstrings) = 0;
    };
    
    #include "cmd_interface.h"				//	cmd_interface.cpp
    #include <sstream>
    
    CMD_Interface ::	CMD_Interface(string* command)
    {
    	m_cmd		= *command;
    }
    CMD_Interface ::	~CMD_Interface(){}
    
    bool		CMD_Interface ::	execute_if_match(string* str)
    {
    	string			buffer;
    	stringstream	sstream;
    	vector<string>	token;
    
    	sstream		<<	*str; 
    	while(sstream >> buffer)	token.push_back(buffer);
    
    	if(token.at(0) == m_cmd)
    	{
    		stringstream	temp;
    		int				value;
    		temp << token.at(1);
    		temp >> value;
    		m_method(&token);
    		return true;
    	}
    	return false;
    }
    
    class cmd_hello : CMD_Interface			//cmd_list.h
    {
    	private:
    		void	m_method(vector<string>* pstrings)
    		{
    			cout << "hello";
    		};
    };
    

    was mag er daran nicht?



  • naja zun├Ąchst mal vererbst du private methoden nicht. die m├╝ssten public sein.

    und wenn du rein virtuelle methoden ├╝berschreiben willst, m├╝ssen die neuen versionen auch virual sein (aber eben nicht pure virutal).

    und ich bin mir nicht ganz sicher ob die private vererbung hier gew├╝nscht ist (kann es nicht beurteilen anhand der bislang gegebenen informationen).



  • edit zum ersten satz:
    die m├╝ssten public ODER PROTECTED sein.



  • Also, das ist schon mal gar nicht m├Âglich - man kann keinen upcast auf eine private Basisklasse machen. Die Fehlermeldung die du bekommst resultiert auch gar nicht aus dem gezeigten Code (abgetippt?).



  • ok das mit procted/Public macht Sinn.

    Ich beschreibe mal genauer was ich vorhabe:
    Ich habe eine Klasse Console, die einen Vector von commands in form von klassen hat.
    eine funktion search() f├╝hrt jetzt f├╝r jeden Eintrag des vectors "execute_if_match(string* str)" aus, bis einer true zur├╝ckgibt.

    execute_if_match() wird dann ja von der entsprechenden klasse ausgef├╝hrt. wie z.b. nach eingabe von: "set_com_port"
    wird search() die klasse cmd_set_com finden, und die von ihr implementierten m_method() ausf├╝hren.

    Ich m├Âchte letztendlich eine sch├Âne Console bauen, die commands h├╝bsch verwaltet, ohne h├Ąssliche case tabellen zu haben.



  • referator schrieb:

    naja zun├Ąchst mal vererbst du private methoden nicht. die m├╝ssten public sein.

    Selbstverst├Ąndlich k├Ânnen die auch private sein.



  • ich hatte sie auf private gesetzt da ich sie nur innerhalb der klasse CMD_interface aufrufen wollte.

    Wenn ich jetzt die einzelnen Kommandoklassen von dem CMD_interface ableite, schreib ich dann private, oder gar nichts? da ich ja eigentlich die CMD_interface klasse haben mag, nur mit spezieller m_method().



  • cl90 schrieb:

    ich hatte sie auf private gesetzt da ich sie nur innerhalb der klasse CMD_interface aufrufen wollte.

    So kann man das auch machen.

    cl90 schrieb:

    Wenn ich jetzt die einzelnen Kommandoklassen von dem CMD_interface ableite, schreib ich dann private, oder gar nichts?

    Gar nicht ist wie private. Du willst aber wohl public.



  • Oh ich glaube grade mein ansatz war einfach falsch.

    ich denke stichwort Strategy w├Ąre hier richtiger.
    Ich werd mich mal einlesen!



  • Und wenn du gerade dabei bist, dein Design zu ├╝berdenken:
    Warum ├╝bergibst du ├╝berall Zeiger auf Objekte, statt sie per-value oder per-reference zu ├╝bergeben? Zeiger k├Ânnen da Sinn machen, wo die Parameter optional sind und nullptr eine g├╝ltige Option sind. Allerdings scheint das bei dir nicht der Fall zu sein, du pr├╝fst nirgendwo, ob deine Zeiger ├╝berhaupt g├╝ltig sind.

    Edit:
    Und poste bitte den vollst├Ąndigen Quelltext. In deiner Header Datei wird nirgends string inkludiert, das sollte dein Compiler schon melden. Und du benutzt irgendwo ein using namespace std; , das geh├Ârt da sicher auch nicht hin.



  • Das mit den pointern hab ich heute von einem Kollegen geh├Ârt.
    Ich werde mir in zukunft die Referenzen angew├Âhnen.



  • Du scheinst das System mit public, protected, private nicht ganz zu verstehen.
    public ist von ├╝berall zugreifbar. Da man die Werte ├Ąndern kann, sollte man Zugriffe ├╝ber Methoden gestalten, um auf fehlerhafte Werte reagieren zu k├Ânnen.
    private ist vor ALLEM versteckt, auch vor abgeleiteten Klassen.
    proteted ist nach au├čen versteckt, aber abgeleitete Klassen k├Ânnen darauf ganz normal zugreifen.

    Wo man bei einer einzelnen Klasse private verwendet, geh├Ârt bei Vererbten oft (aber nicht immer) protected hin.



  • Marthog schrieb:

    Du scheinst das System mit public, protected, private nicht ganz zu verstehen.
    public ist von ├╝berall zugreifbar. Da man die Werte ├Ąndern kann, sollte man Zugriffe ├╝ber Methoden gestalten, um auf fehlerhafte Werte reagieren zu k├Ânnen.
    private ist vor ALLEM versteckt, auch vor abgeleiteten Klassen.
    proteted ist nach au├čen versteckt, aber abgeleitete Klassen k├Ânnen darauf ganz normal zugreifen.

    Wo man bei einer einzelnen Klasse private verwendet, geh├Ârt bei Vererbten oft (aber nicht immer) protected hin.

    und wie schlie├čt du da drauf das ich es nicht verstanden habe?
    Ich nutze das genau so. mit get und set variablen, memberfunktionen und bei vererbungen gebe ich protected.
    trozdem danke, vlt. liest es jemand der es noch nicht wusste



  • Marthog schrieb:

    Wo man bei einer einzelnen Klasse private verwendet, geh├Ârt bei Vererbten oft (aber nicht immer) protected hin.

    Falsch, erstmal sollte alles private sind. Nur bei echt guten Gr├╝nden machst du etwas protected. Ein guter Grund ist zum Beispiel das Template-Method-Pattern.



  • Skym0sh0 schrieb:

    Ein guter Grund ist zum Beispiel das Template-Method-Pattern.

    Noe, ist es nicht.

    #include <iostream>
    
    struct Base
    {
        void f() const
        {
            pre_f();
            std::cout << "f() stuff\n";
            post_f();
        }
    
        virtual ~Base() {}
    
    private:
        virtual void pre_f() const = 0;
        virtual void post_f() const = 0;
    };
    
    struct Derived : Base
    {
    private:
        virtual void pre_f() const override
        {
            std::cout << "pre f() stuff\n";
        }
    
        virtual void post_f() const override
        {
            std::cout << "post f() stuff\n";
        }
    };
    
    int main()
    {
        Derived d;
        d.f();
    }
    

    https://ideone.com/UZ1Fid


Log in to reply