Article source: blog.csdn.net/lifengzhong…

1: Atomic operations – OSAtomic family of functions

All atomic manipulation functions on iOS start with OSAtomic and need to include the header <libkern/ osbase.h >. If different threads operate on the same variable through the atomic manipulation function, the operation of one thread will not affect the operation of the variable in other threads, because these operations are atomic. Because atomic operations can only operate on built-in types, threads that atomic operations can synchronize can only be in the same process’s address space.

2: lock-NSlock series objects

In the iOS platform, the lock object is NSLock object. To enter the lock, call lock function to unlock and call UNLOCK function (because most thread synchronization classes in iOS inherit from NSLocking protocol, lock/unlock function is basically used). After the same NSLock object is successfully called, no thread can lock the NSLock object until it explicitly unlock, thus achieving mutually exclusive access.

NSLock*lock = [[NSLock alloc] init]; [lock lock]; [obj yourMethod]; [lock unlock]; \

In addition to the lock function, other NSLock functions include the tryLock and lockBeforeDate functions. The lock function will block until the lock is successfully held. The tryLock function will try to lock, and if it fails, it will not block. LockBeforeDate blocks until the NSDate date is passed.

In addition to NSLock, iOS also provides lock types of the NSRecursive and NSConditionLock types. The biggest difference between NSRecursive and NSLock is that NSRecursive is reentrant, which means that a thread can call lock multiple times on an NSRecursive object as long as it calls unlock the same number of times. NSConditionLock is a conditional lock object. In addition to the basic lock and unlock functions, NSConditionLock also provides lockWithCondition and unlockWithCondition, which accept integer values as arguments. Only when an unlockWithCondition object is called does the corresponding lockWithCondition return normally. This mechanism is useful when many threads are required to complete a task sequentially, as follows:

[plain] view plaincopy

  1. / / thread A
  2. id condLock = [[NSConditionLock alloc] initWithCondition:NO_DATA];  
  3.    
  4. while(true)  
  5. {  
  6.     [condLock lock];  
  7.     /* Add data to the queue. */  
  8.     [condLock unlockWithCondition:HAS_DATA];  
  9. }  

[plain] view plaincopy

  1. / / thread B
  2. while (true)  
  3. {  
  4.     [condLock lockWhenCondition:HAS_DATA];  
  5.     /* Remove data from the queue. */  
  6.     [condLock unlockWithCondition:(isEmpty ? NO_DATA : HAS_DATA)];  
  7.    
  8.     // Process the data locally.  
  9. }  

\

In addition to generating the NSLock series of objects displayed, you can also achieve synchronization by placing code in @synchronized. A piece of code placed in @synchronized cannot be reentrant by different threads. For example:

[plain] view plaincopy

  1. – (void)myMethod:(id)anObj  
  2. {  
  3.     @synchronized(anObj)  
  4.     {  
  5. // Only one thread of code can execute at a time.
  6.     }  
  7. }  

The NSLock family of objects are namable, that is, they can be used to synchronize threads within different processes. \

3: event – NSCondtion

The NSConditon type provides the wait and signal functions, which represent the operations that wait for an event and those that trigger an event, respectively. In addition to the wait function, NSCondition also provides the waitUntilDate function, which has much the same functionality as lockBeforeDate in NSLock. In short, it provides a wait function with a timeout.

While NSCondition does much the same thing that the Event type does in a Windows environment, NSConditon behaves a little strangely to a developer familiar with the Event type:

Firstly, because of the NSLocking protocol, NSCondition calls lock and unlock functions before and after the triggering and waiting process. As mentioned before, when an object following the NSLocking protocol calls lock, other lock calls of this object will be blocked. If thread A fires the event, thread B receives the event, and thread B waits for the event to fire after calling the lock function, then thread A will never fire the event again. The secret lies in the call of the wait function. In fact, the unlock function is called inside the wait function. In other words, after the call of the WATi function, the NSCondition object is unlocked, so thread A can lock the object and trigger the NSCondition object. When an event triggered by other threads inside the wait function been informed of this event is triggered, then the incident to call the lock function, then the function returns, and on the outside of the function, it looks as if receive events threads never let go of NSCondition the ownership of the object and thread B directly triggered by the blocking state entered the state.

Second point: When multiple threads are blocked, waiting for the same AutoReset Event object to be fired, there is no fixed order in which threads will be woken up in Windows. That is, the operating system does not provide any guarantee as to which threads will be woken up. On the iOS platform, the author tested that the order in which the wait function is triggered is related to, and only related to, the order in which the wait function is called, and has no relation to other conditions (such as thread priority). This requires additional consideration during development.

Third point: The wait function is not completely trusted. NSCondtion does not require an additional variable to avoid abnormal wait returns. This method is used to ensure synchronization between threads. The specific code is as follows:

[plain] view plaincopy

  1. // The thread waiting for the event to fire
  2. [cocoaCondition lock];  
  3. while (timeToDoWork <= 0)  
  4.     [cocoaCondition wait];  
  5.    
  6. timeToDoWork–;  
  7.    
  8. // Do real work here.  
  9.    
  10. [cocoaCondition unlock];  
  11.   
  12. // Start the thread of the event
  13. [cocoaCondition lock];  
  14. timeToDoWork++;  
  15. [cocoaCondition signal];  
  16. [cocoaCondition unlock];  

The timeToDoWork is the extra variable that is required in the use of NSCondition.

NSConditon objects are also named, that is, they can be synchronized with threads within different processes.

\

The thread synchronization mechanism on iOS is a bit thin compared to the rich thread synchronization mechanism provided on Windows, but this simplicity makes it easier to use.

\

Reference:iOS Developer Liabray

* * * *

Sample code source:Thread Programming Guide

\

Note: the thread synchronization referred to in this article generally refers to synchronization and mutual exclusion in multi-threaded environment.

\