Faul singleton in einer Multithread-c# - Anwendung
Arbeite ich an einem Multithread-c# - Anwendung, die nutzen eines WCF web service. Die Verbindung zu dem webservice haben ein bestimmtes Zeitlimit, das wir uns definieren können und danach wird es enger. Ich bin auf der Suche um die Verbindung zu speichern, um die web-service-Nutzung des singleton-Klasse. Ich werde versuchen, die Instanz wie folgt :
CLazySingleton ins = CLazySingleton.Instance;
string connection = CLazySingleton.abc;
Unten ist der code für die singleton-Klasse :
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace LazySingleton
{
public class CLazySingleton
{
private static readonly Lazy<CLazySingleton> _instance
= new Lazy<CLazySingleton>(() => new CLazySingleton());
private static readonly object ThreadLock = new object();
public static string abc;
//I will use the service connection object in place of 'abc' in the application
//assume that 'abc' is storing the connection object
private CLazySingleton()
{ }
public static CLazySingleton Instance
{
get
{
if (abc == null)
{
lock (ThreadLock)
{
//Make the connection
abc = "Connection stored in this variable";
Console.WriteLine("Connection Made successfully");
return _instance.Value;
}
}
else
{
return _instance.Value;
}
}
}
}
}
Meine Fragen sind :
1. Würde dieser code in der Lage sein, um zu kümmern, mehrere threads versuchen, um die Instanz in der gleichen Zeit ? Dies ist derzeit meine größte Sorge.
2. Kann ich eine bessere Lösung dafür ?
3. Benötige ich für die Verwendung von 'lock' hier oder über Lazy-Ansatz kümmert sich um multithreads zu versuchen, um die Instanz ?
Jede mögliche Hilfe würde geschätzt.
Dank !
Ich habe einige Zweifel auf Ihrem Ansatz. Warum müssen Sie pflegen ein Singleton für die Verbindung? Ist es ein problem, wenn jeder thread bekommt seinen eigenen proxy/connection? Und da es ein web-Dienst, den ich nicht voraussehen, keine Probleme, wenn Sie viele verbindungen. --- Um besser zu verstehen welche Art von Objekt das ist Ihre "Verbindung"?
Sie brauchen nicht die Sperre
InformationsquelleAutor Anubhav Sharma | 2013-03-05
Du musst angemeldet sein, um einen Kommentar abzugeben.
Laut Microsoft ist Lazy Initialisierung - Dokumentation unter dem Abschnitt "Thread-Safe "Initialisierung":
Mit diesem im Verstand, Ihre
abc
Feld muss nicht statisch sein. Wie man mit einemLazy<T>
zu instanziieren Sie Ihr singleton ist, es ist sicher zu initialisieren, die Verbindung in derCLazySingleton
Konstruktor.Ich denke, mit Singleton ist nicht das richtige Muster hier, eigentlich brauchen Sie nicht zu verwalten, Ihre Verbindung auf diese Weise. Und, sind Sie sicher, dass Sie einen Webdienst aufrufen, weil das, was ist die Art von timeout, die Sie hier erwähnen?
InformationsquelleAutor Richard
Einfache Nutzung ThreadSafetyMode
Danke, ich werde sicherlich versuchen, diese.
InformationsquelleAutor TalentTuner
In Ihrem Szenario kann der "abc" - Feld initialisiert zweimal. Stellen Sie sich die situation, das "abc" der Variablen null ist. Erste thread in dem "lock" sperren, bevor die Wertzuweisung. Der zweite thread wartet, bevor die Sperre. So der erste thread wird initialisiert, die "abc" und der zweite thread neu initialisiert werden (Ihre überprüfung auf null ist, außerhalb der Sperre, das ist der Grund). Aber vielleicht ist dies nicht etwas, das man fürchten sollte.
Ja, Sie können. Lassen Sie mich beschreiben, es im letzten block dieser Antwort.
Erstellung der Value-Eigenschaft in der Lazy-Klasse ist thread-sicher. In deinem Szenario würde ich verwenden, den Vorteil der Eigenschaft IsValueCreated von Faul<> Klasse. Sie benötigen noch die Schraubensicherung-Objekt als gut. Nur eine weitere Sache ist, dass wenn Sie der Eigenschaft Value des Lazy<> - Klasse, IsValueCreated Eigenschaft true zurück (das ist der trick 😉 )
InformationsquelleAutor David Gregor