I've begun controlling queues for the first time and feel like I have a good handle on how to use them and kudos to Apple for making them quite straightforward to use.
What I encountered, however, is the challenge of multiple threads reading and writing to the same objects. In this question I got this fine answer, and it leaves me asking for some confirmation from everyone to make sure I understand the pros and cons of @synchronized
vs GCD dispatch_barrier_async
.
This is the way I see it:
@synchronized
PRO: You can wrap any object in @synchronized
as long as you have access/pointer to it, making it easy for shared data models to be safely handled from different objects in the program
PRO: Supported by iOS 4 (and maybe earlier)
`dispatch_barrier_async` with custom DISPATCH_QUEUE_CONCURRENT
PRO: Is faster than @synchronized
CON: DISPATCH_QUEUE_CONCURRENT only available in iOS 5 (as discussed here), so not available for supporting iOS 4
CON: Not as easy to use when controlling read/write on an object from many other objects, since queues are most easily available only to the object that creates them (without some work to go around this limitation)
In summary, the best tool depends on the needs of the program, in consideration of the above.
If anyone has something to add or point out, I'd appreciate it.
Well, a few things to point out:
1) When you use @synchronized, it pulls in the WHOLE exception framework for iOS (or OSX) for an app. I know of this on OSX and it has a performance impact there, cannot say for sure on iOS but would expect the same. That said, this is using a sledgehammer to drive in a nail - that capability was around way before other options were available. I personally avoid its use like the plague, and have ported other open source frameworks to use dispatch semaphores (I thank Mike Ash (again) for that!)
2) Your comment about "DISPATCH_QUEUE_CONCURRENT" is a red herring of sort - since iOS 4 the system has given you 3 concurrent queues so you really are pushing the envelope if you need to define your own. With dispatch, you have async and sync, serial and concurrent, groups that you can wait on, dispatch after. There is such a richness here how could you even think of 1). The more you use blocks the more you will use them!
EDIT: I used custom concurrent queues in my iOS 4.3 app, along with all the Mike Ash barrier techniques. The queue.h file shows it as available:
__OSX_AVAILABLE_STARTING(__MAC_10_6,__IPHONE_4_0)
DISPATCH_EXPORT DISPATCH_CONST DISPATCH_WARN_RESULT DISPATCH_NOTHROW
dispatch_queue_t
dispatch_get_global_queue(dispatch_queue_priority_t priority, unsigned long flags);
/*!
* @const DISPATCH_QUEUE_SERIAL
* @discussion A dispatch queue that invokes blocks serially in FIFO order.
*/
#define DISPATCH_QUEUE_SERIAL NULL
/*!
* @const DISPATCH_QUEUE_CONCURRENT
* @discussion A dispatch queue that may invoke blocks concurrently and supports
* barrier blocks submitted with the dispatch barrier API.
*/
#define DISPATCH_QUEUE_CONCURRENT (&_dispatch_queue_attr_concurrent)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With