Spezialisierung/Überladen von Methoden



  • Hallo!

    Ich sitze jetzt schon eine gefühlte Ewigkeit an diesem Problem und komme zu keiner Lösung, hier eine vereinfachte Beschreibung des Problems:

    template<class T>
    class A 
    {
    public:
      template<class X>
      void func(int z, X* _dummy)
      {
      }
    
      template<class X>
      void func(int z, A<X>* _dummy)
      {
      }
    };
    

    es wird immer die allgemeinere Methode aufgerufen, egal von welchem Typ der 2. Parameter ist. Ich weiß dass das hier keine Spezialisierung mehr ist, sondern lediglich eine Überladung, mit Spezialisierung ist das glaub ich gar nicht möglich.

    Viell. gibt es hier ja einige Templatespezialisten die mir helfen können oder mich aufklären dass das so nicht funktionieren kann.

    Mit freundlichen Grüßen 🙂 ,
    McLovin_



  • Also

    #include <iostream>
    #include <cstdlib>
    using namespace std;
    
    template<class T>
    class A
    {
    public:
      template<class X>
      void func(int z, X* _dummy)
      {
          cout<<"X\n";
      }
    
      template<class X>
      void func(int z, A<X>* _dummy)
      {
          cout<<"A<X>\n";
      }
    };
    
    int main()
    {
        A<int> a;
        int i=2;
        a.func(1,&a);
        a.func(1,&i);
    }
    

    zuigt bei mir an:

    A<X>
    X
    

    Was soll es anzeigen?



  • Eigentlich genau das, aber bei mir wird immer nur die obere Methode aufgerufen.

    Das Beispiel ist zwar sehr vereinfacht aber sollte im Prinzip gleich sein... bei mir ist der 3. Parameter ein Member der Klasse mit typ T*... und ich übergebe die parameter nicht mit dem referenzOperator sondern direkt als pointer.



  • Geht mein Code bei Dir auch schief oder hast Du einen Microsoft-Compiler?



  • Ich verwende einen MS Compiler, aber habs gerade getestet, kommt das richtige raus. Ich werd jetzt mal die relevanten Teile aus dem Source original rauskopieren. Moment



  • Mach bitte eine kleine eigenständige main.cpp zum Testen.



  • template<typename T>
    struct array {
    
    private:
      T* _values;
      int _size;
      long _start;
      long _end;
    
    public:
    
    void init(int amount, ...) {
      va_list l;
      va_start(l,amount);
      init(amount, l, _values);
    }
    
    void init(va_list arg) {
      int l,u;
      l = va_arg(arg,int);
      u = va_arg(arg,int);
      cout << "_start: " << l << std::endl;
      cout << "_end: " << u << endl;
      _start = l;
      _end = u;
      assert(_end >= _start);
      _size = 1 + _end - _start;
      cout << "_size: " << _size << endl;
      _values = new T[_size];
    }
    
    template<class S>
    void init(int amount, va_list arg, array<S>* _dummy)
    {
      std::cout << "amount: " << amount << std::endl;
      if(amount >= 2) 
      {
        init(arg);
        amount -= 2;
        if(amount >= 2) 
        {
          for(int i = 0; i < _size; i++) 
          {
            _values[i].init(amount,arg);
          }
        }
      }
    }
    
    template< template<class> class H, class S>
    void init(int amount, va_list arg, H<S>* _dummy)
    {
      std::cout << "amount: " << amount << std::endl;
      init(arg);
    }
    
    };
    

    Also das hier ist der code, von außen wird lediglich die Funktion init(int ammount, ...) aufgerufen, danach soll intern jenachdem ob unser T ein weiteres Array ist oder nicht die zugehörige init Funktion aufrufen.



  • Sry hab den Post von dir zu spät gesehen, hier die main:

    int main()
    {
      array<pli_varray<int>> vv1;
      vv1.init(4,1,3,5,6);
    }
    

    das hier reicht schon, entweder im Debugger durchgehen und nachsehen welche init Funktion aufgerufen wird, oder auf die Memory Access Violation achten :D.

    Danke!! (Der Code oben ist aber nicht der komplette, sind lediglich die init Funktionen rauskopiert, aber alles andere ist eigentlich nicht Relevant für die Funktionen)



  • vv1[1][3] = 6;
    

    Das hier noch in der Main einfügen, sry wegen Doppelpost.



  • Also array würde ich das nicht nennen. Nicht nur, dass das mit std::array Probleme geben könnte, sondern auch, weil es einen POD Typen impliziert. Warum nicht gleich std::array nutzen?

    #include <array>
    
    int main()
    {
      std::array<int, 6> a = {3, 5, 34, 7, 6};
    }
    


  • pli_varray?
    Also lauffähig ist das noch nicht.



  • es heißt eh nicht genau array, hab es zur Vereinfachung umbenannt.

    Und wie gesagt es ist hier nur die Funktionalität der inits, es erfüllt schon den Zweck eines Arrays. Zum POD typen: es gibt auch ctor/dctor etc.

    Der 2 Index bei meinem vorigen Post sollte 5 sein, nicht 3.

    std::array kommt nicht in Frage weil die Größe nicht statisch bekannt ist, ich mach das nicht privat für mich, es gibt hier leider einige Vorgaben die mit den Eigenschaften des Projekts verbunden sind.



  • volkard schrieb:

    pli_varray?
    Also lauffähig ist das noch nicht.

    Sry das sollte array heißen 🙂



  • McLovin_ schrieb:

    volkard schrieb:

    pli_varray?
    Also lauffähig ist das noch nicht.

    Sry das sollte array heißen 🙂

    Und noch ein Fehler.
    Mach eine main.cpp die geht. Das Gestückel ist ja ätzdend.



  • Und std::vector kannst du auch nicht benutzen, weil? Sorry für die Fragen die nichts mit deinem Problem zu tun haben, aber mir scheint das ganze lässt sich doch so viel besser lösen.



  • Kein Problem cooky451, es war nicht meine Idee es so zu realisieren, ich bin erst vor kurzem zum Projekt hinzugekommen, std::vector ist keine schlechte Idee, haben auch schon überlegt nicht eine map zu verwenden.

    @Volkard, sry wegen den Fehler, aber es hat sich schon erledigt, der Fehler lag wo anders, danke für deine Zeit.


Anmelden zum Antworten