Es ist selten, dass NSLock
das richtige Werkzeug für den Job ist. Es gibt jetzt viel bessere Werkzeuge, besonders mit GCD; später mehr.
Wie Sie wahrscheinlich schon von the docs wissen, aber ich werde für diejenigen wiederholen Mitlesen:
Achtung: Die NSLock Klasse verwendet POSIX-Threads seine Sperrverhalten zu implementieren. Wenn Sie eine Entsperrungsnachricht an ein NSLock-Objekt senden, müssen Sie sicherstellen, dass die Nachricht von demselben Thread gesendet wird, der die ursprüngliche Sperrnachricht gesendet hat. Das Entsperren einer Sperre aus einem anderen Thread kann zu einem nicht definierten Verhalten führen.
Das ist sehr schwer ohne Deadlocking zu implementieren, wenn Sie versuchen, auf verschiedenen Threads zu sperren und entsperren. Das grundlegende Problem ist, dass, wenn lock
blockiert den Thread, dann gibt es keine Möglichkeit für die nachfolgende unlock
jemals auf diesen Thread laufen, und Sie können nicht unlock
auf einem anderen Thread. NSLock
ist nicht für dieses Problem.
Anstatt NSLock
können Sie die gleichen Muster mit dispatch_semaphore_create()
implementieren. Diese können sicher in jedem beliebigen Thread aktualisiert werden. Sie können sperren mitund Sie können entsperren mit dispatch_semaphore_signal()
. Das heißt, diese immer noch ist normalerweise nicht die richtige Antwort.
Die meisten Ressourcenkonflikte werden am besten mit einer Operationswarteschlange oder einer Dispatchwarteschlange verwaltet. Diese bieten hervorragende Möglichkeiten, parallel zu arbeiten, Ressourcen zu verwalten, auf Ereignisse zu warten, Erzeuger-/Verbrauchermuster zu implementieren und ansonsten fast alles zu tun, was Sie in der Vergangenheit mit einem NSLock
oder NSThread
gemacht hätten. Ich empfehle die Concurrency Programming Guide als eine Einführung in das Design mit Warteschlangen statt Sperren.