Basic knowledge of
The concept of RunLoop
Runloop can be thought of as an event-driven circle. When we perform events, gestures, time responses, etc., we need listeners. This is where the concept of sources comes from.1. The input source 2. Time source
—- pseudocode is as follows:
while (true) {[[NSRunLoop currentRunLoop] runMode:NSRunLoopCommonModes beforeDate:[NSDate distantFuture]];
}
Copy the code
Note:
The main thread starts a Runloop by default,while the asynchronous thread does not. The while prevents the Runloop from sleeping, and the Runloop automatically starts sleeping when there is no “event source” to drive it
Input source
Includes three types: NSPort, custom source, performSelector: OnThread: delay
2.1 NSPort Port-based source
Cocoa and Core Foundation provide built-in support for port-based sources created using port-related objects and functions. In Cocoa you never have to create an input source directly. You simply create the port object and add it to the Run loop using the NSPort method. The port object handles creating and configuring the input source.
There are three types of NSPort: NSMessagePort (basically abandoned), NSMachPort, and NSSocketPort. The NSURLConnection in the system is based on NSSocketPort communication, so when using NSURLConnection in the background thread, you need to manually start the RunLoop, because the RunLoop in the background thread is not started by default.
NSURLConnection *connection = [[NSURLConnection alloc] initWithRequest:request delegate:self startImmediately:NO];// Temporarily not running
[connection scheduleInRunLoop:[NSRunLoop currentRunLoop] forMode:NSRunLoopCommonModes];/ / use NSRunLoopCommonModes
[connection start];
Copy the code
You can use NSMachPort as a communication channel between threads. For example, when the main thread creates a child thread, it passes in an NSPort object, so that the main thread can communicate with the child thread. To achieve two-way communication, the child thread also needs to pass back an NSPort object to the main thread
2.2 Custom Sources
In Core Foundation applications, you must use CFRunLoopSourceRef type-dependent functions to create a custom input source, followed by a callback function to configure the input source. Core Fundation calls callbacks when appropriate to handle input events and clean up sources. Common touch, scroll events, and so on are such sources, implemented internally by the system. Normally we would not use this provenance, and the third case has met our needs
2.3 performSelector: OnThread
Cocoa provides input sources that can perform selectors in any thread. As with port-based sources, Perform Selector requests are serialized on the target thread, mitigating many of the synchronization problems that can easily be caused on a single thread. And unlike port-based sources, perform Selector automatically clears the Run loop when it executes. This method is simple and practical, and more widely used.
performSelectorOnMainThread:withObject:waitUntilDone:
performSelectorOnMainThread:withObject:waitUntilDone:modes:
performSelector:onThread:withObject:waitUntilDone:
performSelector:onThread:withObject:waitUntilDone:modes:
performSelector:withObject:afterDelay:
performSelector:withObject:afterDelay:inModes:
cancelPreviousPerformRequestsWithTarget:
cancelPreviousPerformRequestsWithTarget:selector:object:
Copy the code
The last two of these apis are to cancel a call in the current thread, and the other apis are to execute a specified @selector in the main thread or in a Run Loop under the current thread.
Time source
Note that the Timer generated at the beginning of scheduledTimerWith**** will automatically load the current RunLoop in default NSDefaultRunLoopMode. Other generated timers require you to manually add -addTimer:forMode to the Run Loop. It is important to note that the Timer firing does not cause the Run Loop to return.
[[NSRunLoop currentRunLoop] addTimer:_timer forMode:NSRunLoopCommonModes];
[[NSRunLoop currentRunLoop] runMode:NSRunLoopCommonModes beforeDate:[NSDate distantFuture]];
Copy the code
RunLoop observer
A CFRunLoopObserverRef object can be created to detect the working state of the RunLoop. It can detect the following events of the RunLoop: Run loop entry Run loop is about to start timing Run Loop is about to process input source Run Loop is about to sleep Run loop is woken up but terminates before the wake up event is executed
1. Run Loop Modes
Mode | Name | Description |
---|---|---|
Default | NSDefaultRunLoopMode (Cocoa) kCFRunLoopDefaultMode (Core Foundation) | By default, all operations are included, and this mode is used in most cases, the default running mode, except for events on NSConnection objects |
Connection | NSConnectionReplyMode (Cocoa) | This mode is used to handle callback events for NSConnection |
Modal | NSModalPanelRunLoopMode (Cocoa) | Modal mode, in which RunLoop only handles modal-related events |
Common Modes | NSRunLoopCommonModes (Cocoa) kCFRunLoopCommonModes (Core Foundation) | This mode is used to configure group mode. If an input source is associated with this mode, the input source is associated with all modes in the group |
Event Tracking | NSEventTrackingRunLoopMode (Cocoa) | This mode is used to handle window events, mouse events, etc |
Note: NSRunLoopCommonModes is a set of commonly used modes, NSDefaultRunLoopMode, NSTaskDeathCheckMode, UITrackingRunLoopMode. The advantage of this mode is that if the asynchronous thread now has a timer started, Do not append in all runloop modes, just append once in NSRunLoopCommonModes
Reference connection:
IOS Multithreaded Programming Part 1/3 – NSThread & RunLoop 3 Run Loops 4.Cocoa Learn more about NSOperationQueue, NSRunLoop and Thread safety