Statische Methoden überschreiben



  • Darf man statische Methode in einer abgeleiteten Klasse überschreiben?



  • Meines wissens darf man das, aber man sollte es grundsätzlich nicht tun:

    class Base
    {
    public:
      static void f() { cout << "Base" << endl; }
    }
    
    class Derived : public Base
    {
    public:
      static void f() { cout << "Derived" << endl;
    }
    
    int main()
    {
      Derived * dp = new Derived;
      Base * bp = dp;
    
      dp->f();  // gibt Derived aus
      bp->f();  // gibt Base aus
    }
    

    Das ist wohl kaum das gewünschte Ergebnis, daß sich die Klasse je nachdem, über welchen Pointer Du sie ansprichst ein andere Verhalten zeigt.
    Und daran wird sich auch nichts ändern lassen, denn was Du hier bräuchtest wäre ne virtuelle Funktion, damit die Funktion vom dynamischen Typen des Objekts abhängt. Leider bedeutet static aber soviel wie: gehört zur Klasse, nicht zum Objekt... und kann damit auch vom dynamischen Typ des Objekts abhängen. Kurz: virtual und static schließen sich aus.

    MfG Jester



  • nolta schrieb:

    Darf man statische Methode in einer abgeleiteten Klasse überschreiben?

    Was statische Methode angeht, darf der Begriff "überschreiben" kaum verwendet werden. Da die Klasse, zu der die Methode gehört, als noch ein Parameter der Methode betrachtet werden kann, geht es in der Situation um "überladung".



  • desert pinguin schrieb:

    nolta schrieb:

    Darf man statische Methode in einer abgeleiteten Klasse überschreiben?

    Was statische Methode angeht, darf der Begriff "überschreiben" kaum verwendet werden.

    Soweit so gut.

    Da die Klasse, zu der die Methode gehört, als noch ein Parameter der Methode betrachtet werden kann, geht es in der Situation um "überladung".

    Da irrst du dich. Es geht hier weder um Überladung noch um Überschreiben. Überladen kann man nur Namen innerhalb *eines* Scopes. Überschreiben nur virtuellen Funktionen.

    Beides trifft hier nicht zu. Definiert eine abgeleitete Klasse eine statische Methode mit dem selben Namen wie eine Basisklasse, so überdeckt (hiding) die neue Methode die der Basisklasse.

    Beispiel:

    struct Bar
    {
        static void func(int);
    };
    
    struct Foo : Bar
    {
        static void func();
    };
    
    int main()
    {
        Foo::func();   // OK
        Foo::func(2);  // ERROR! Bar::func(int) nicht sichtbar!
        Foo f;
        f.func();      // OK
        f.func(2);     // ERROR! Bar::func(int) nicht sichtbar!
    }
    


  • HumeSikkins schrieb:

    desert pinguin schrieb:

    nolta schrieb:

    Darf man statische Methode in einer abgeleiteten Klasse überschreiben?

    Was statische Methode angeht, darf der Begriff "überschreiben" kaum verwendet werden.

    Soweit so gut.

    Da die Klasse, zu der die Methode gehört, als noch ein Parameter der Methode betrachtet werden kann, geht es in der Situation um "überladung".

    Da irrst du dich. Es geht hier weder um Überladung noch um Überschreiben. Überladen kann man nur Namen innerhalb *eines* Scopes. Überschreiben nur virtuellen Funktionen.

    Beides trifft hier nicht zu. Definiert eine abgeleitete Klasse eine statische Methode mit dem selben Namen wie eine Basisklasse, so überdeckt (hiding) die neue Methode die der Basisklasse.

    Beispiel:

    struct Bar
    {
        static void func(int);
    };
    
    struct Foo : Bar
    {
        static void func();
    };
    
    int main()
    {
        Foo::func();   // OK
        Foo::func(2);  // ERROR! Bar::func(int) nicht sichtbar!
        Foo f;
        f.func();      // OK
        f.func(2);     // ERROR! Bar::func(int) nicht sichtbar!
    }
    

    Gut. Du hast vollkommen recht.
    Ich habe das mit auf Java bezogenen Definitionen verwechselt.

    public class Test {
    
    public static void main(String[] args){
      A.f();
      B.f();
      }
    }
    class A{
    public static void f(){
    }
    }
    
    class B extends A{
    //Das ist eine Überladung
    public static void f(int a){
    }
    
    //Das ist eine Überdeckung
    //public static void f(){
    //}
    }
    

    Das obige Beispiel kompiliert sich ohne Problem.
    Ich würde sagen, dass das ein Beispiel ist, mit dem man das Konzept von Überladung illustrieren kann.



  • Ich würde sagen, dass das ein Beispiel ist, mit dem man das Konzept von Überladung illustrieren kann

    Ich verstehe ehrlich gesagt nicht, was der Java Code tun soll, außer Verwirrung zu stiften.
    In C++ kann man Überladung nur innerhalb eines Scopes illustrieren, da sie nur so funktioniert. Da Klassen nun aber jeweils einen eigenen Scope besitzen, kannst du Überladung in C++ nicht über Klassengrenzen hinaus (Basisklasse, abgeleitete Klasse) illustrieren. Zumindest solange du keine using-Deklaration einfügst:
    http://fara.cs.uni-potsdam.de/~kaufmann/?page=GenCppFaqs&faq=Overload#Answ



  • HumeSikkins schrieb:

    Ich verstehe ehrlich gesagt nicht, was der Java Code tun soll, außer Verwirrung zu stiften.

    Der Code stellt den Unterschied zwischen Java und C++ dar.
    In Java kann man statische Methoden nicht nur innerhalb eine Klasse überladen.

    HumeSikkins schrieb:

    In C++ kann man Überladung nur innerhalb eines Scopes illustrieren, da sie nur so funktioniert. Da Klassen nun aber jeweils einen eigenen Scope besitzen, kannst du Überladung in C++ nicht über Klassengrenzen hinaus (Basisklasse, abgeleitete Klasse) illustrieren. Zumindest solange du keine using-Deklaration einfügst:
    http://fara.cs.uni-potsdam.de/~kaufmann/?page=GenCppFaqs&faq=Overload#Answ

    Du hast vollkommen recht, was C++ angeht. Ich habe mich geirrt.



  • desert pinguin schrieb:

    Der Code stellt den Unterschied zwischen Java und C++ dar.

    Ja schon, aber in C gibts doch gar keine Klassen 😕



  • Shade Of Mine schrieb:

    desert pinguin schrieb:

    Der Code stellt den Unterschied zwischen Java und C++ dar.

    Ja schon, aber in C gibts doch gar keine Klassen 😕

    Sicher 😃
    Da die beiden Sprachen (Java/C++) die Begriffe (Überladung, Überschreibung und Überdeckung) besitzen, passt deine Ironie hier nicht 👍.
    Das finde Ich interessant, zumindest fuer mich, die zu vergleichen.



  • desert pinguin schrieb:

    Das finde Ich interessant, zumindest fuer mich, die zu vergleichen.

    Der Vergleich ist, dass man in C++ ein
    using Base::foo;
    braucht, in Java nicht.
    Also ich sehe allen ernstes keinen interessanten Vergleich. Interessant wäre es, wenn Java und C++ die Überladung generell anders realisieren würden - tun sie aber, soweit ich das sehe, nicht.



  • Shade Of Mine schrieb:

    desert pinguin schrieb:

    Das finde Ich interessant, zumindest fuer mich, die zu vergleichen.

    Der Vergleich ist, dass man in C++ ein
    using Base::foo;
    braucht, in Java nicht.
    Also ich sehe allen ernstes keinen interessanten Vergleich. Interessant wäre es, wenn Java und C++ die Überladung generell anders realisieren würden - tun sie aber, soweit ich das sehe, nicht.

    Gut, dass alles in Butter ist.


Anmelden zum Antworten