J'ai lu différentes opinions sur le motif singleton. Certains soutiennent qu'il devrait être évité à tout prix et d'autres qu'il peut être utile dans certaines situations.
Une situation dans laquelle j'utilise des singletons est quand j'ai besoin d'une fabrique (disons un objet f de type F) pour créer des objets d'une certaine classe A. La fabrique est créée une fois à l'aide de certains paramètres de configuration, puis est utilisée chaque fois qu'un objet de le type A est instancié. Ainsi, chaque partie du code qui veut instancier A récupère le singleton f et crée la nouvelle instance, par exemple
F& f = F::instance();
boost::shared_ptr<A> a = f.createA();
Donc, le scénario général est que
- Je n'ai besoin que d'une seule instance d'une classe soit pour des raisons d'optimisation (je n'ai pas besoin de plusieurs objets d'usine) ou pour partager un état commun (par exemple, l'usine sait combien d'instances de A elle peut encore créer)
- J'ai besoin d'un moyen d'avoir accès à cette instance f de F à différents endroits du code.
Je ne souhaite pas savoir si ce modèle est bon ou mauvais, mais en supposant que je souhaite éviter d'utiliser un singleton, quel autre modèle puis-je utiliser?
Les idées que j'avais étaient (1) d'obtenir l'objet d'usine à partir d'un registre ou (2) de créer l'usine à un moment donné pendant le démarrage du programme, puis de transmettre l'usine comme paramètre.
Dans la solution (1), le registre lui-même est un singleton, donc je viens de déplacer le problème de ne pas utiliser un singleton de l'usine au registre.
Dans le cas (2), j'ai besoin d'une source initiale (objet) d'où provient l'objet d'usine, j'ai donc peur de retomber à un autre singleton (l'objet qui fournit mon instance d'usine). En suivant cette chaîne de singletons, je peux peut-être réduire le problème à un singleton (toute l'application) par lequel tous les autres singletons sont directement ou indirectement gérés.
Cette dernière option (en utilisant un singleton initial qui crée tous les autres objets uniques et injecte tous les autres singletons aux bons endroits) serait-elle une solution acceptable? Est-ce la solution qui est implicitement suggérée lorsque l'on conseille de ne pas utiliser de singletons, ou quelles sont les autres solutions, par exemple dans l'exemple illustré ci-dessus?
MODIFIER
Puisque je pense que le point de ma question a été mal compris par certains, voici quelques informations supplémentaires. Comme expliqué par exemple ici , le mot singleton peut indiquer (a) une classe avec un objet instance unique et (b) un modèle de conception utilisé pour créer et accéder à un tel objet.
Pour clarifier les choses, utilisons le terme objet unique pour (a) et motif singleton pour (b). Donc, je sais ce que sont le modèle singleton et l'injection de dépendances (BTW, dernièrement, j'utilise fortement DI pour supprimer les instances du modèle singleton d'un code sur lequel je travaille).
Mon point est qu'à moins que le graphe d'objet entier soit instancié à partir d'un seul objet vivant sur la pile de la méthode principale, il sera toujours nécessaire d'accéder à certains objets uniques via le modèle singleton.
Ma question est de savoir si la création et le câblage d'un graphique d'objet complet dépendent de la méthode principale (par exemple via un cadre DI puissant qui n'utilise pas le modèle lui-même) est la seule solution sans modèle singleton .