Qual è corretto modo per inizializzare un membro statico di tipo 'T &' in una classe template?
-
21-09-2019 - |
Domanda
sto giocando intorno con una classe Singleton generica ansioso-inizializzazione. L'idea è che si eredita dalla classe pubblicamente in questo modo:
class foo : public singleton<foo> { };
Ho imparato molto nel processo, ma mi sono bloccato in questo momento perché è spezzando il Visual Studio 2008 linker. Il problema è con l'elemento istanza statica e / o l'inizializzazione.
template<class T>
class singleton {
singleton();
singleton(singleton const &);
singleton & operator = (singleton const &);
public:
static T & instance;
};
template<class T> T & T::instance;
Tutta la comprensione sarebbe molto apprezzato!
EDIT:
Con questa dichiarazione di classe ...
template<class T>
class singleton {
singleton();
singleton(singleton const &);
singleton & operator = (singleton const &);
public:
static T instance;
};
template <class T> T singleton<T>::instance;
Quando provo a fare questo ...
class foo : public singleton<foo> { };
ottengo questo errore ...
C2248 errore: 'Singleton :: Singleton' : Non può accedere membro privato dichiarato nella classe 'Singleton'
...
Questa diagnostica è verificato nel compilatore generato funzione 'foo :: foo (void)'
La mia interpretazione è che Singleton vuole costruire un oggetto foo, che, per eredità, dipende dalla costruzione di un singoletto il cui costruttore è privato. Ho pensato Singleton avrebbero accesso a un proprio costruttore, ma credo di no. Tutte le idee?
EDIT 2:
Ho capito che l'approccio di ereditare dal singleton<T>
ha il problema di richiedere modifica alla classe per essere usato come un Singleton. Ho finito con il seguente codice per il mio modello di classe Singleton ansioso-inizializzazione.
template<typename T>
class singleton_wrapper {
singleton_wrapper();
singleton_wrapper(singleton_wrapper const &);
singleton_wrapper & operator = (singleton_wrapper const &);
static T instance;
template<typename T> friend T & singleton();
};
template<typename T> T singleton_wrapper<T>::instance;
template<typename T>
T & singleton() {
return singleton_wrapper<T>::instance;
}
Per la classe ...
class foo {
public:
void bar() { }
};
... Si potrebbe accedere a una singola istanza di esso (inizializzato prima di main ()) usando il seguente:
singleton<foo>().bar();
Grazie ancora per l'aiuto, in particolare Gman. Sono molto contento della mia prima esperienza sulla pila trabocco .
Soluzione
Non è possibile, in quanto non si dispone di un'istanza concreta. È possibile necessario creare un caso reale che si può fare riferimento a:
template <class T>
class singleton {
...
private:
static T instance_;
public:
static T& instance;
};
template <class T> T singleton<T>::instance_;
template <class T> T& singleton<T>::instance = singleton<T>::instance;
O, più semplicemente, basta fosso il riferimento del tutto:
template <class T>
class singleton {
...
public:
static T instance;
};
template <class T> T singleton<T>::instance;
Altri suggerimenti
Off-the-manica:. Cambia esempio essere di tipo 'T' invece di 'T &'