Junior
Hogyan működik a szemétgyűjtő (garbage collector)?
sobes.tech MI
Válasz az MI-től
Az iOS/macOS fejlesztés kontextusában a Swift/Objective-C nem szemétgyűjtőt (GC) használ, hanem automatikus hivatkozásszámlálást (Automatic Reference Counting, ARC).
Az ARC automatikusan kezeli a memóriát azzal, hogy számolja az erős hivatkozások (Strong) számát minden osztálypéldányra (és zárványokra, amelyek fogva tartják). Amikor az erős hivatkozások száma nullára csökken, a rendszer felszabadítja az objektum által foglalt memóriát.
Az ARC főbb pontjai:
- Erős hivatkozások (Strong): Növelik a hivatkozásszámot. Az objektum a memóriában marad, amíg legalább egy erős hivatkozás van rá.
- Gyenge hivatkozások (Weak): Nem növelik a hivatkozásszámot. Az erős ciklusok elkerülésére használják. Opcióként hivatkoznak egy objektumra, és nil lesz, amikor az objektum felszabadul.
- Nem birtokolt hivatkozások (Unowned): Nem növelik a hivatkozásszámot. Akkor használják, ha az objektumok életciklusa ismert, és egy objektum mindig létezik, amíg egy másik. A hivatkozás nem opcionális. Ha az unowned hivatkozott objektum felszabadul, a hozzáférés futási hibát eredményez.
Az ARC fordítási időben működik, és a megfelelő kódba retain (szám növelése) és release (szám csökkentése) hívásokat illeszt be.
class MyClass {
var prop: String = ""
}
var reference1: MyClass? = MyClass() // Szám = 1
var reference2 = reference1 // Szám = 2
reference1 = nil // Szám = 1
reference2 = nil // Szám = 0, az objektum felszabadul
class Person {
let name: String
weak var apartment: Apartment? // Gyenge hivatkozás a ciklus elkerülése érdekében
init(name: String) { self.name = name; print("\(name) inicializálva") }
deinit { print("\(name) deinitializálva") }
}
class Apartment {
let unit: String
unowned var tenant: Person // Nem birtokolt hivatkozás
init(unit: String, tenant: Person) { self.unit = unit; self.tenant = tenant; print("Lakás \(unit) inicializálva") }
deinit { print("Lakás \(unit) deinitializálva") }
}