ARC and memory management in Swift
How reference counting manages object lifetimes, and how to break strong reference cycles.
Read the Korean original on Velog ↗English translation

Swift rarely requires us to free objects manually because ARC tracks their references for us. That convenience does not mean every memory-management problem disappears.
References and the heap
Instances of reference types are allocated on the heap. Their memory must eventually be released by the program or its memory-management system.
Before ARC, Objective-C code commonly managed ownership explicitly with operations such as
retainandrelease.
Automatic Reference Counting
ARC automates memory management by tracking strong references. The compiler inserts the necessary retain and release operations when references are created or removed. The insertion happens at compile time; the resulting operations run as the program executes.
Swift documentation: Automatic Reference Counting Swift uses Automatic Reference Counting (ARC) to track and manage your app’s memory usage. In most cases, this means that memory management “just works” in Swift, and you don’t need to think about memory management yourself. ARC automatically frees up the memory used by class instances when those instances are no longer needed.
Reference counting
Creating a strong reference keeps an instance alive. Releasing that reference reduces the number of owners. Once no strong references remain, the instance can be deallocated.
class Human {
let name: String
let age: Int
init(name: String, age: Int) {
self.name = name
self.age = age
}
}
// Create an instance with a strong reference
var snack: Human? = Human(name: "snack", age: 28) // Count(1)
// Another strong reference keeps the same instance alive
var sunday: Human? = Human(name: "sunday", age: 26) // Count(2)

// Release a strong reference to the instance
snack = nil // Count(1)
// Release a strong reference to the instance
sunday = nil // Count(0)
// Deallocate when no strong references remain

Strong reference cycles
Two or more objects can hold strong references to one another, keeping their reference counts above zero even when the rest of the application no longer needs them. These cycles cause memory leaks. Choosing weak or unowned references where appropriate breaks the cycle without giving up the relationship between the objects.

Further reading: Swift: Automatic Reference Counting.