du point de vue d'un utilisateur final API qui doit "obtenir public class Bar
{
private Bar() { }
// Do you prefer a Property?
public static Bar Instance
{
get
{
return new Bar();
}
}
// or, a Method?
public static Bar GetInstance()
{
return new Bar();
}
}
7 Réponses :
en C #, je préférerais loin .Instance code>, car il s'inscrit dans les directives générales. P>
@Mickel Injection de dépendance couplée à un modèle singleton?
Personnellement, je n'ai même jamais écrit de singleton code> pour mon propre légitime, et je suis généralement douteux de son besoin.
@Silky Que faites-vous dans le cas d'une winform qui ne devrait vraiment être créé que comme un exemple unique sur plusieurs DLL?
@Silky Ils sont utilisés beaucoup plus que ce qu'ils devraient être, pour être sûr - mais à tout moment, nous devons faire face au fait que les ressources disponibles sont finies, nous ne pouvons pas éviter les globaux d'une sorte. Un singleton n'est qu'un moyen formalisé d'appliquer un global.
Michael Todd: Je n'ai jamais écrit une "vraie" application Winforms :) Juste de ma propre expérience.
Rex: En effet, je ne doute pas de l'idée en général, juste en pratique, je ne trouve pas que cela revient souvent.
Je suis d'accord avec cela avec une condition supplémentaire: en raison de l'exigence de pureté implicite des getters de propriété, la propriété code> ne doit pas i> créer l'instance si l'on n'existe pas actuellement. Pour ce cas, vous devez le créer avec un initialiseur de champ (
FieldType de champ statique = Nouveau champ de terrain () code>) ou à l'intérieur d'un constructeur statique.
dépend. Avez-vous besoin de passer des paramètres? Si c'est le cas, je ferais de la mainse (). Sinon, cela n'a probablement pas d'importance (du moins d'un point de vue appelant, car ils sont vraiment les deux méthodes de toute façon; Cependant, il est em> compte si vous essayez d'être davantage basé sur les normes et, Dans ce cas, une instance semble être meilleure). P>
Je préfère la propriété, ce sont des modèles standard. P>
Comme avec à peu près tout, cela dépend:) p>
Si le singleton est chargé de paresseux et représente plus qu'une quantité triviale de travail à instancier, alors getInstance () est plus appropriée, comme une invocation de méthode indique que le travail est en cours. P>
Si nous masquons simplement pour protéger l'instance Singleton, une propriété est préférable. P>
Mais spécifiquement pour un singleton, seule la première invocation devrait faire le travail. Les invocations suivantes devraient simplement renvoyer l'instance précédemment préparée.
@Hans, bien sûr, mais dans un singleton chargé de paresseux, l'appelant ne sait pas si cela a été instancié, chaque appel est potentiellement le lourd.
Si vous souhaitez créer Singleton, vous ne pouvez pas simplement retourner un nouvel objet sur chaque getInstance code> instance d'appel ou
instance code> Propriété getter. Vous devriez faire quelque chose comme ceci:
public sealed class Bar
{
private Bar() { }
// this will be initialized only once
private static Bar instance = new Bar();
// Do you prefer a Property?
public static Bar Instance
{
get
{
return instance;
}
}
// or, a Method?
public static Bar GetInstance()
{
return instance;
}
}
Es-tu sûr? Je pensais la même chose au début, mais le constructeur privé garantit que cette classe peut créer des instances de soi. En tout cas, vous pouvez supprimer le constructeur privé dans le vôtre.
@Rayell, je pense que son échantillon de code est juste de démontrer la différence entre la propriété et la méthode.
@Y - Si vous supprimez avec le CTOR privé, il y a un CORTOR I> - pas ce que nous voulons. Et oui: pour un singleton, vous devez absolument réutiliser instance code> (ou similaire).
Le constructeur privé permet de créer les instances que par les membres de la classe. Et c'est ce qui se passe dans le code. Cela fonctionnera, mais ce ne sera pas un singleton. Vous aurez une nouvelle instance créée à chaque fois pour utiliser la propriété instance code> ou
geInstance () code> méthode.
@Rex m - Je suis au courant de cela et j'ai donné ma réponse ci-dessus. Je pensais juste que c'est une bonne idée de signaler une faille dans l'exemple de code, car il est écrit que cela devrait être singleton.
@MARC Gravell Tu as raison, mais je dirais que le singleton ne devrait pas tenir des références à elle-même. Il devrait y avoir une barsingleton qui passe le même exemple de barreau. Imo.
@Y - Vraisemblablement un type imbriqué? Oui, cela fonctionne aussi et aide à garder le avant championner code> trucs bien rangé.
@Y - Peut-être que cela vous aidera à comprendre, msdn.microsoft.com/fr- US / Bibliothèque / MS998558.aspx
Comme @Rex a dit, cela dépend de la sémantique que vous voulez transmettre. P>
getinstance () n'implique pas nécessairement une instance singleton. Donc, j'utiliserais getinstance () dans le cas où la création d'instance se produit à la demande, de nouvelles nouvelles n'est pas souhaitable et que l'instance pourrait être, mais n'est pas garantie d'être identiques. Les pools d'objets correspondent également à ces critères. (En fait, un singleton est une spécialisation d'un pool d'objets avec préservation de l'État: -)) p>
La propriété d'instance statique en revanche implique une identité d'instance singleton et préservée. P>
BTW, comme @Rayell mentionné votre exemple de code n'est pas un singleton, vous ne devriez donc pas utiliser la propriété d'instance. Vous pouvez toujours utiliser la méthode getinstance () dans ce cas, car elle servirait d'usine d'instance. P>
if (uniqueInstance == null) { uniqueInstance = new Singleton(); }
Belle double vérification verrouillée. Bien que si vous n'avez besoin que d'instancier votre singleton, utilisez: Privé Statique Radio Singleton Singleton OprinSInstance = New Singleton ();
"Obtenir une instance" devrait vraiment être "Obtenir l'instance" - et le nouveau
nouveau code> est un peu trompeur ;-p
@MARC Gravell - accepté. point bien pris. THX
S'il vous plaît réfléchissez à deux fois avant d'écrire un singleton. J'ai vu des cas où ils ont forcé l'utilisation d'essais d'intégration sur des tests d'unité - les singletons accèdent à une base de données et d'autres classes leur sont couplées. Voir Stackoverflow.com/questions/137975/...
Comme je le pense et lisez les commentaires, la propriété .Instance implique vraiment que seule une "instance unique existe". Tandis que .getinstance () pourrait être interprété comme "Obtenir une instance", telle qu'une usine.
@Truewill - Yep, d'accord. Je rééchappe la classe pour éviter le singleton. Je suppose que la question originale est toujours valide ... c'est ... si vous avez absolument besoin de manière positive d'un singleton, si un tel cas existe;)
Je suis ma hâte de poster la question que j'ai négligée que la classe d'origine persistait une seule instance (à httpcontext) et une nouvelle instance n'était pas créée à chaque appel à .Instance. Je devrais mettre à jour l'exemple de code d'origine, mais @rayell fournit une solution correcte ci-dessous.