Sobes.tech
Middle

Mis on unowned Swiftis ja kuidas seda kasutatakse?

sobes.tech AI

Vastus AI-lt

Unowned viide (nõrk kaudse omandi) Swiftis kasutatakse selleks, et vältida tugeva omandi tsükleid (retain cycles), kui kaks objekti viitavad üksteisele tugevalt, takistades nende vabanemist mälust.

unowned omadused:

  • Tagab, et objekt, millele viitab unowned viide, alati eksisteerib kuni selle kasutamiseni.
  • Kui proovite pääseda unowned viidetele pärast seotud objekti vabastamist, tekib jooksuaegne viga (runtime crash).
  • Kasutatakse siis, kui viidatud objekti elutsükkel pole pikem kui viitava objekti elutsükkel. Teisisõnu, unowned viide ei tee objekti tugevamaks.

Näide kasutamisest sulgemise haaramisel:

class Customer {
    let name: String
    var card: CreditCard?

    init(name: String) {
        self.name = name
    }

    deinit {
        print("\(name) vabastatakse")
    }
}

class CreditCard {
    let number: UInt64
    unowned let customer: Customer // Unowned viide Customer-ile

    init(number: UInt64, customer: Customer) {
        self.number = number
        self.customer = customer
    }

    deinit {
        print("Kaart #\(number) vabastatakse")
    }
}

var john: Customer? // Valikuline Customer
john = Customer(name: "John Appleseed")
john!.card = CreditCard(number: 1234_5678_9012_3456, customer: john!)

// Kui määrame nil, vabastatakse Customer ja Card,
// kuna puudub tugev tsükkel
john = nil 

Teine näide — unowned kasutamine sulgemise haaramisel:

class HTMLElement {
    let name: String
    let text: String?

    lazy var asHTML: () -> String = { [unowned self] in // Kasutades unowned self
        if let text = self.text {
            return "<\(self.name)>\(text)</\(self.name)>"
        } else {
            return "<\(self.name) />"
        }
    }

    init(name: String, text: String? = nil) {
        self.name = name
        self.text = text
    }

    deinit {
        print("\(name) vabastatakse")
    }
}

var paragraph: HTMLElement? // Valikuline HTML element
paragraph = HTMLElement(name: "p", text: "tere maailm")
print(paragraph!.asHTML())

// Kui määrame nil, vabastatakse HTMLElement, kuna sulgemine ei hoia seda tugevalt
paragraph = nil

Valik unowned ja weak sõltub sellest, kas viide võib muutuda nil-iks objekti elutsükli jooksul. Kui viide mitte kunagi ei saa muutuda nil-iks enne objekti vabastamist, kasutage unowned. Kui võib — kasutage weak.