2012-10-12 13 views
6

Sto cercando di compilare il seguente pezzo di codice compilatore, ma sembra che ci sia un problema che non riesco a risolvere:C++ e CRTP implementazione del modello e il dilemma

template <int x> 
struct count_x 
{ 
    enum { x_size = x }; 
}; 

template <typename y> 
struct crtp_base 
{ 
    typedef typename y::count_t count_t; 
    crtp_base(const count_t&){} 
}; 

template <int x> 
struct derived : public crtp_base<derived<x> > 
{ 
    typedef typename count_x<x> count_t; 
    typedef crtp_base<derived<x> > base_t; 
    derived(const count_t& c) : base_t(c){} 
}; 


int main() 
{ 
    derived<2> d((count_x<2>())); 
    return 0; 
} 

Quando compilati wth clang 3.1, il seguente è l'errore:

c:\clangllvm\code\example.cc:18:21: error: expected a qualified name after 'typename' 
    typedef typename count_x<x> count_t; 
        ^
c:\clangllvm\code\example.cc:18:21: error: typedef name must be an identifier 
    typedef typename count_x<x> count_t; 
        ^~~~~~~~~~ 
c:\clangllvm\code\example.cc:18:28: error: expected ';' at end of declaration list 
    typedef typename count_x<x> count_t; 
         ^
          ; 
c:\clangllvm\code\example.cc:20:18: error: no template named 'count_t'; did you mean 'count_x'? 
    derived(const count_t& c) 
       ^~~~~~~ 
       count_x 
c:\clangllvm\code\example.cc:2:8: note: 'count_x' declared here 
struct count_x 
    ^
c:\clangllvm\code\example.cc:20:18: error: use of class template count_x requires template arguments 
    derived(const count_t& c) 
       ^
c:\clangllvm\code\example.cc:2:8: note: template is declared here 
struct count_x 
    ^
5 errors generated. 

credo che ha qualcosa a che fare con il modo in cui i modelli sono determinati al momento della compilazione e se sono determinati come un tipo al momento giusto. Ho anche provato ad aggiungere "using base_t :: count_t;" senza alcun risultato. Oltre a questo, la diagnostica prodotta dal compilatore mi ha lasciato davvero perso. Sarebbe gradita una risposta o un suggerimento su qualcosa da leggere su questo errore.

risposta

2

count_x<x> non è un nome qualificato (non ha alcun ::!), Quindi non può essere preceduto con typename.

Una volta risolto questo problema, il codice non riuscirà ancora perché i typedef nidificati del tipo derivato non sono stati ancora visualizzati dal compilatore quando istanzia la base CRTP. Questo other question mostra alcune alternative.

+0

'È un errore utilizzare il disambigificatore del nome quando non è necessario ', in realtà penso che sia falso. –

+0

@Jesse Credo che sia stato un errore in C++ 03, ma ho smesso di essere in C++ 11. –

+0

@Martinho: Ho apportato questa modifica, ora fornisce un altro insieme di errori: c: \ clangllvm \ code \ example.cc: 10: 24: errore: nessun tipo denominato 'count_t' in 'derivato <2>' typedef typename y: : count_t count_t; ~~~~~~~~~~~~^~~~~~~ c: \ clangllvm \ code \ example.cc: 15: 25: nota: nell'istanza della classe template 'crtp_base >' richiesto qui struct derivato: crtp_base pubblico > ^ c: \ clangllvm \ code \ example.cc: 25: 15: Nota: in istanza di classe template 'derivato <2>' richiesto qui derivato <2> d ((count_x <2>())); – Switzy

Problemi correlati