J'essaie de mettre en œuvre un simple gestionnaire de plugins en utilisant les concepts trouvés dans this answer. Je l'implémente en tant que modèle afin de pouvoir instancier différents gestionnaires pour les plugins implémentant différentes interfaces.Utilisation du paramètre de modèle comme argument dans un modèle
Cependant, je ne peux pas le compiler.
Voici un extrait qui illustre le problème:
#include <map>
#include <string>
template<typename InterfaceType>
class PluginManager {
public:
// Map between plugin name and factory function
typedef std::map<std::string, InterfaceType*(*)()> map_type;
static InterfaceType *createInstance(std::string const& plugInName) {
map_type::iterator iter = map().find(plugInName);
if (iter == map().end())
return 0;
return iter->second();
}
protected:
static map_type & map() {
static map_type map;
return map;
}
};
class MyInterface {};
PluginManager<MyInterface> myInterfacePluginManager;
int main(int argc, char *argv[]) {
}
Lorsque vous essayez de le compiler, voici ce qui se passe:
$ g++ pimgr_bug.cpp
pimgr_bug.cpp: In static member function ‘static InterfaceType* PluginManager<InterfaceType>::createInstance(const std::string&)’:
pimgr_bug.cpp:12: error: expected ‘;’ before ‘iter’
pimgr_bug.cpp:13: error: ‘iter’ was not declared in this scope
pimgr_bug.cpp:15: error: ‘iter’ was not declared in this scope
Il semble être lié à la définition de map_type: si Je le modifie pour que le type de valeur de carte soit une classe concrète qu'il compile correctement, mais avec le type de valeur défini comme InterfaceType*(*)()
ou tout autre élément lié à InterfaceType, alors cela ne fonctionne pas. La carte est supposée contenir une correspondance entre le nom du plugin et le pointeur vers une fonction d'usine correspondante. Il me manque presque certainement quelques notions de base de la syntaxe du template!
Est-il possible de créer une carte dans un modèle qui contient un type défini par l'un des arguments du modèle? J'utilise gcc 4.4.7 et malheureusement je ne peux pas utiliser C++ 11 (si c'est pertinent).
Merci!
Essayez d'ajouter "typename", c'est-à-dire "typename map_type :: iterator". –
gcc 4.8 donne un message d'erreur plus utile: * besoin de 'typename' avant' PluginManager :: map_type :: itérateur' car 'PluginManager :: map_type' est une portée dépendante * –
Walter
@MichaelAaronSafyan qui l'a corrigé. .. S'il ne s'agit pas d'un doublon, veuillez l'ajouter comme réponse – harmic