Angenommen, ich habe diese Methode:
%Vor% Hier ist das Verhalten, das Foo
haben soll:
Wenn thread 1 Foo(1)
aufruft und thread 2 Aufrufe Foo(2)
aufruft, können beide Threads gleichzeitig ausgeführt werden.
Wenn thread 1 Foo(1)
aufruft und thread 2 Aufrufe Foo(1)
aufruft, können beide Threads nicht gleichzeitig ausgeführt werden. p>
Gibt es einen guten Standardweg in .net
, um diese Art von Verhalten anzugeben? Ich habe eine Lösung, die ein Wörterbuch von Objekten zum Sperren verwendet, aber das fühlt sich irgendwie unordentlich an.
Verwenden Sie ein Wörterbuch, das verschiedene Sperrobjekte für die verschiedenen Argumente bereitstellt. Richten Sie das Wörterbuch ein, wenn Sie das zugrunde liegende Objekt (oder statisch, falls zutreffend) instanziieren:
%Vor%Und dann benutze es in deiner Methode:
%Vor%Ich würde nicht sagen, dass diese Lösung unordentlich ist, im Gegenteil: Die Bereitstellung einer feinen Sperrgranularität ist lobenswert, und da Sperren für Werttypen in .NET nicht funktionieren, ist die Verwendung einer Zuordnung die naheliegende Lösung.
>Seien Sie jedoch vorsichtig: Das obige funktioniert nur so lange, wie das Wörterbuch nicht gleichzeitig geändert und gelesen wird. Es empfiehlt sich daher, das Wörterbuch nach der Einrichtung als schreibgeschützt zu behandeln.
Unterste Zeile: Sie können Werttypen nicht sperren.
Das Wörterbuch, das Sie verwenden, ist der beste Ansatz, den ich mir vorstellen kann. Es ist kludsey, aber es funktioniert.
Ich persönlich würde eine architektonische Lösung verfolgen, die das Sperren überflüssig macht, aber ich weiß nicht genug über Ihr System, um Ihnen Hinweise zu geben.
Die Verwendung von Dictionary reicht nicht aus, Sie sollten "ConcurrentDictionary" verwenden oder eine Datenstruktur implementieren, die Multi-Thread-Zugriff unterstützt.
Erstellen eines Wörterbuchs & lt; & gt; damit du einen Wert sperren kannst erscheint mir Overkill. Ich habe das mit einer Schnur arbeiten lassen. Es gibt Leute (zB Jon Skeet), die diesen Ansatz nicht mögen (und aus berechtigten Gründen - siehe diesen Beitrag: Ist es OK, eine Zeichenfolge als Sperrobjekt zu verwenden? )
Aber ich habe eine Möglichkeit, diese Bedenken zu mildern: passe die Zeichenfolge im laufenden Betrieb an und kombiniere sie mit einer eindeutigen Kennung.
%Vor%Was passiert ist, dass verschiedene Werte in einem String-internen Pool gespeichert werden (der AppDomain-Grenzen überschreitet). Durch das Hinzufügen von lockIdentifier zum String wird sichergestellt, dass der String nicht mit internierten Strings kollidiert, die in anderen Anwendungen verwendet werden. Dies bedeutet, dass die Sperre nur in Ihrer eigenen Anwendung wirksam wird.
Der interne Pool wird also einen Verweis auf eine interne Zeichenfolge zurückgeben - dies ist in Ordnung, um zu sperren.
Tags und Links .net c# concurrency