Kann der msvc sowas nicht?



  • template<class T,T t>class foo{};
    template<template<class T,T>class f=foo>class bar
    :public f<int,4>{};
    

    Oder was ist an dem Code falsch?



  • Mhm, irgendwie versteh ich gar nicht was das bezwecken sollte 😕

    Könntest du mal erklären was du damit erreichen willst? Vielleicht gäbs ne andere Variante ans Ziel zu kommen...



  • Er will bar als template argument eine template classe mit ner 'class T, T t' parameter liste übergebn können.

    Hab das eben mal VC++.Net zu schlucken geben.. wirklick interessant... solage foo nur ein template parameter hat geht, sobald nen 2. dazu baue dessen typ in parameter 1 übegeben wird gehts nimmer.. hmmm... mal sehen über ich MS überlisten kann... 😃



  • Ja bitte, mir wills nämlich net gelingen... Übrigens (falls das hilft...):

    template<int i>class foo{};
    template<template<int>=foo>class bar{};
    

    geht...



  • Also das logischste ist meiner Meinung nach:

    template<class T,T t>
    class foo{};
    template<class f=foo>
    class bar : public f{};
    

    Instanziierung dann zb so:

    bar<foo<int,4> > test;
    

    Damit hast du nämlich gleich zwei Probleme beseitigt:
    a) es lässt sich kompilieren *g*
    b) Das Problem mit deiner Basisklasse existiert nicht mehr. Falls dir dieses Problem nicht bewusst sein sollte, mag ich's dir kurz erklären. Vorausgesetzt, dein Code ließe sich kompilieren, dann gibt es bei folgender Deklaration ein Problem:
    [cpp]template<class T,T t>class foo{};
    template<template<class T,T>class f=foo>class bar
    :public f<int,4>{}; //<--

    bar<foo<CString, "Hello World"> > test; //<--[/cpp]

    Das Problem sind die markierten Stellen:
    Einmal übergibst du CString, einmal int ...

    Was willst du damit erreichen, dass du die templateklasse in der templatedefinition drinne hast? Dass man nur Klassen die auf dieser Vorlage basieren, übergeben kann?



  • Also, das Problem ist mir klar... Das war ja auch nur ein Bsp... Im richtigen code würde ich das natürlich anders schreiben. Ja, ich brauch das genau so (in etwa 😃 ) Das ganze nennt sich plocy-basiertes Klassendesign...
    Zu deiner Lösung:

    class Widget{};
    template<class W=Widget>class Dialog{};
    template<class W,class D>class DialgMgr{...};
    
    //Anwendercode:
    class ExtWidget
    :public Widget{};
    typedef DialgMgr<ExtWidget,Dialog<> >MyMgr;    //Hoppla
    

    Und das ist nichtmal aus der Luft gegriffen.
    Außerdem: Ich behaupte, deinen code würde er nicht mal kompilieren, wenn meins ginge. Man muss nämlich

    typedef bar<foo> foobar;
    

    Schreiben...

    //Und wenn du glück hast geht das weiter: (Bibliothekskode)

    template<class W,class D>
    void DialgMgr<W,D>::AddToDialog(const Info<W>& info, const D& dialog,unsigned x,unsigned y)
    {
        W* new_w=new W(info);
        D.add(W,x,y);
    };
    
    template<class W>
    void Dialog<W>::add(W pwi,unsigned x,unsigned y)
    {
        pair<unsigned,unsigned> k(x,y);
        pair<W,pair<unsigned,unsigned> >p(*pwi,k);    //Fehler!
        widgets.push_back(p);
    };
    

    OK, das ganze Beispil ist designtechnisch Unsinn...



  • Tut mir leid, wenn ich dienen Code jetzt nicht anguck, nur so viel: Meins kompiliert 😉



  • pair<W,pair<unsigned,unsigned> >p(*pwi,k);    //Fehler!
    

    😕

    Denke mal du meinst so was:

    pair<W,pair<unsigned,unsigned>>p(*pwi,k);    //Fehler! 
    // der dumme macht jetzt ein typedef, der schlaue das hier:
    pair<W,pair<unsigned,unsigned> >p(*pwi,k);    // kein Fehler!
    

    😃 :p



  • Nein. Worauf ich hiauswollte ist das das ExtWidget zwar angenommen, aber nur der Widget Teil übernommen wird. Was ich eigentlich bezwcken wollte, ist zu zeigen das ich das eben brauch. Notfalls werde ich den Kompiler wechseln, da man mir gesagt hat das der code von gcc kompiliert würde... Aber das ist dann eher der letzte Ausweg...


Anmelden zum Antworten