Blog - How ARC works — Automatic Reference Counting
Retain, release, weak/unowned, reference cycles, and what the compiler inserts for you in Objective-C and Swift.
- Author
- 2code
- Published
- Tags
- iOS
- ARC
- memory
ARC (Automatic Reference Counting) is the memory model in Objective-C and for classes in Swift: an object lives as long as something holds a strong reference to it.
Reference count
Each object has a count .
- strong assignment:
- end of a strong reference’s lifetime:
- when →
deinit/dealloc, memory returns to the system
The compiler inserts retain / release (or equivalents) — it is not a heap-scanning garbage collector.
Strong, weak, unowned
…
- strong (default) — owner; keeps the object alive.
- weak — does not increment ; becomes
nilwhen the object is freed. - unowned — does not increment ; you assert the object still lives (crash otherwise).
Retain cycles
Classic leak:
Then and forever. Fix: one side weak (e.g. delegate), or unowned when lifetime is guaranteed.
In Swift closures:
someAsync { [weak self] in
guard let self else { return }
self.update()
}
Without [weak self], the closure often retains self → a cycle with its owner.
ARC ≠ GC
| ARC | GC | |
|---|---|---|
| When it cleans | immediately at | periodically / in pauses |
| Cycles | you must break them | usually detected |
| Predictability | low latency | possible stutter |
That is why ARC fits iOS UI well: no surprise GC pauses, but cycles are your job.
Autorelease (ObjC)
Historically, an object can enter an autorelease pool and receive release later (e.g. end of the run loop). ARC still cooperates; in tight loops @autoreleasepool { ... } can prevent temporary-object buildup.
Takeaway
ARC is simple on the happy path and demanding on object graphs. Rule of thumb: one strong ownership path, break cycles with weak, especially for delegates and closures.