Различия @synchronized() и NSLock
У меня есть блок кода, к которому часто обращаются, и из основного потока или нескольких других потоков фона. Мне нужно убедиться, что этот код обрабатывается только по одному.
В настоящее время я использую блок @synchronized(self) { }
, но я не уверен, что это обеспечит правильную защиту. Как он отличается от экземпляра NSLock
?
Наконец, может ли кто-нибудь предложить, как я могу защитить свой метод? Этот метод находится в моем делете приложения, и я обращаюсь к нему из разных потоков, вызывая:
[[[UIApplication sharedApplication] delegate] myMethod];
Большое спасибо,
Mike
Ответы
Ответ 1
В блоге Google Mac есть замечательная запись в блоге о внутренней работе @synchronized
:
http://googlemac.blogspot.com/2006/10/synchronized-swimming.html
В настоящее время я использую @synchronized (self) {} block, но я не уверены, что правильная защита. Как он отличается из экземпляра NSLock?
Существует несколько способов синхронизации критических разделов (@synchronized, NSLock, OSSpinLock,...).
Я думаю, что @synchronized
является наиболее удобным (а также самым медленным).
Вот хороший ответ SO, который объясняет различия между @synchronized и NSLock.
Вы получаете доступ к вашему методу через общий экземпляр (который в основном является одноэлементным) делегатом. Возможно, вы можете переосмыслить свой дизайн и выяснить способ, который позволяет заблокировать меньшую часть кода в myMethod
.
Ответ 2
Если у вас действительно есть что-то, что вы хотите обрабатывать по одному элементу за раз, я рекомендую использовать NSOperations и NSOperationQueue, где вы установили maxConcurrentOperationCount равным 1. Если вы убедитесь, что единственный способ, которым это Доступ к разделяемому блоку кода осуществляется через операции в этой очереди, вы избавитесь от необходимости дорогостоящих блокировок.
Это может потребовать небольшой реорганизации вашего приложения, но я обнаружил, что применение этого в моих собственных приложениях привело к повышению производительности и более чистого кода.