Sperren auf Feld oder lokale Variable?

8

Nachdem ich diese Frage gelesen habe eine Antwort von Marc ....

Manchmal sehe ich Leute, die eine lokale Variable sperren.

Ist dieser Code kaputt?

%Vor%

Ich glaube, object o = new Object(); sollte außerhalb der Methode als Field sein.

Da jeder Thread eine neue Instanz von o erhält, gibt es mehrere Sperren.

Was fehlt mir hier? Sollte es in diesem speziellen Fall keine Felder sperren?

    
Royi Namir 07.01.2013, 09:37
quelle

5 Antworten

8
  

Ich glaube Objekt o = neues Objekt (); sollte außerhalb der Methode als Feld sein.

     

Da jeder Thread eine neue Instanz von o erhält, gibt es mehrere Sperren.

     

Gibt es irgendetwas, was mir hier fehlt? weil ich weiß, dass es Felder sperren sollte (in diesem speziellen Fall).

Ihr Verständnis ist richtig. Der Code ist kaputt. In dieser Implementierung wird, obwohl die Sperre aktiv ist, keine Synchronisierung bereitgestellt, da sie sich auf verschiedenen Objekten befindet.

Von MSDN-Sperre c #

  

Vermeiden Sie im Allgemeinen das Sperren für einen öffentlichen Typ oder Instanzen, die nicht von Ihrem Code gesteuert werden. Die allgemeinen Konstrukte lock (this), lock (typeof (MyType)) und lock ("myLock") verletzen diese Richtlinie:

     
  • lock (this) ist ein Problem, wenn auf die Instanz öffentlich zugegriffen werden kann.
  •   
  • lock (typeof (MyType)) ist ein Problem, wenn MyType öffentlich zugänglich ist.
  •   
  • lock ("myLock") ist ein Problem, da jeder andere Code, der denselben String verwendet, denselben Zugriff hat.
  •   

Bewährte Methode besteht darin, ein privates Objekt zum Sperren oder eine private statische Objektvariable zu definieren, um die für alle Instanzen gemeinsamen Daten zu schützen.

    
Tilak 07.01.2013, 09:48
quelle
5

Ja. Es ist kaputt.

Sie möchten ein statisches schreibgeschütztes Objekt als privates Feld zum Sperren. Wie Sie vermuten, erstellt Ihr Beispielcode jedes Mal ein neues Objekt, wenn Sie Do aufrufen, und daher hat die Sperre nichts zu halten und wird überhaupt nicht funktionieren.

%Vor%     
Michael Viktor Starberg 07.01.2013 09:45
quelle
2

Sie erstellen das Objekt o jedes Mal, wenn Ihre Methode aufgerufen wird. Also, die Sperre funktioniert nicht. Ich meine, andere Threads werden nicht darauf warten, dass die Sperre nicht signalisiert wird, und die Kontrolle über eine Ressource übernehmen, die diese Sperre steuert. Normalerweise sind Sperrobjekte eine private Variable in einer Klasse, so dass alle Methoden in dasselbe Objekt schauen.

    
platon 07.01.2013 09:40
quelle
2

Ich persönlich sehe keinen Grund, dies zu verwenden, da lock nur das spezielle Feld in der -Instanz von o auf den signalisierten Status setzt. Daher können andere Threads den Status dieser Instanz überprüfen und basierend darauf den Code innerhalb der lock -Anweisung ausführen oder die Ausgabe davon warten.

Wenn Sie jedes Mal eine lokale Variable haben, wird eine neue Instanz zugewiesen, so dass es für jeden Thread in Ordnung ist.

Sieh darin keinen Sinn.

    
Tigran 07.01.2013 09:40
quelle
1

Locking auf lokale Variable, die Sperre gewann die Arbeit. Das Sperren der globalen Variable kann wirksam werden, um mehrere Threads zu synchronisieren.

%Vor%     
terwxqian 26.08.2017 09:00
quelle