Occurrence scenario In Controller B there is a NSTimer
You create it and attach it to the main runloop
Then when exiting Controller B, I forgot to turn off the timer. Controller B will not be released, and B and timer will have a circular reference because self is written directly into the timer when it is created. Method 1 Since we can't pass self directly, let's try passing weakSelf
The test result shows that a circular reference still occurs. B is not released, and timer has a strong reference to the weakSelf variable. Timer -> weakSelf -> B -> timer forms a circular reference among the three. Method 2 Set up a wrapper class, wrap Controller B and put it in the timer, like this I think Controller B is several MB in size, and leaking it is a waste of memory. WeakWrap is only a few hundred bytes, so it doesn't matter if it leaks. WeakWrap has a weak reference to Controller B. WeakWrap wraps Controller B and passes it into the timer. Even if you forget to turn off the timer, only WeakWrap and timer will be leaked. Theoretically, there are still memory leaks, but they are relatively rare. If a Controller is frequently entered and exited, one timer is lost every time it enters and exits. If there are dozens of leaked timers hanging on the main run loop, it will affect performance and smoothness. If you want dozens of timers to fire at the same time and call the timer event response method, the overhead is still quite large. Method 3 NSTimer is known to strongly reference the parameter target:self. If you forget to close the timer, anything you pass in will be strongly referenced. Just implement a timer. The function of a timer is to call a method at a fixed time. The calling time of NSTimer is not accurate! It is hung on the runloop and is affected by thread switching and the execution time of the previous event. Use dispatch_asyn() to execute functions at a fixed time. See the following code.
Dispatch_async loop does not generate recursive calls dispatch_async adds a task to the queue, and GCD calls back [weakSelf loop] This method solves the problem that the timer cannot be released and cannot be removed from the runloop. Using this method, I wrote a timer that does not have a circular reference. When the controller is released, the timer will also stop releasing automatically. You can even write self directly in the timer block without a circular reference. GitHub download address Method 4 I have never encountered the problem of circular references in NSTimer before, because I have always used them in pairs, opening them in viewWillAppear and closing them in viewWillDisappear. If they are not closed, so many timers mounted on the runloop will affect the performance and fluency. Just like managing memory, if the application and release are used in pairs, there will be no leakage. The principle of whoever applies should release. However, if the team is large, others may make mistakes and cause leakage, which can be solved from the technical point of view and the team programming standards. For example, some specifications are set, such as the controller must be successfully destroyed when exiting, and memory cannot be leaked. Self cannot be written in Block, etc. |
<<: When knowledge graphs “meet” deep learning
>>: Android resolution adaptation test
Li Xingxing's PR video editing cheats + PR ed...
We all know that when live streaming sells goods ...
The Qin and Han dynasties are collectively known ...
Despite having become mainstream over the past fe...
After the news that Beijing Hyundai's five ma...
Beijing will carry out antigen testing among peop...
(Photo courtesy of TUCHONG Creative) Recently, th...
The latest practical course on making money with ...
According to the Shanghai Municipal Market Superv...
Since 2015, the traffic dividend of China's m...
Spring is here and summer is approaching. In the ...
One of the eternal themes of human spaceflight is...
1. Background 1.1 Boosting Boosting[1] is a class...
Today I will show you how to play the crowd pack ...