I fell into this trap and had a retain cycle.
So if you have ever written code like foo.runOnCompletion(myHandler)
, where myHandler
is your own instance method, then you will have a memory issue when foo
object retains the closure.
Let’s jump straight to fixing it first, which is:
foo.runOnCompletion { [weak self] in
self?.myHandler()
}
Tada! weak self
to the rescue.
That is the usual way to writing a closure. And Swift language has been nice 🫶🏻 to force us to remind ourselves whenever self will be retained. Tough love to speak.
ie. If you omit capturing self as weak
or unowned
, which would imply strong capturing, then you are forced to use self
every time within the closure –> remind us self is being strongly retained.
What’s the pitfall then?
Going back to foo.runOnCompletion(myHandler)
.. I was not forced to write self.myHandler
, so I was led to thinking that there is no retain cycle on self
.
As you now know, that is incorrect.
The topic was also discussed in Swift Forum.
Hopefully Swift will improve, providing a way to pass a func weakly.
I am sure everyone is sick of writing tons of publisher.sink { [weak self] in ... }