Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why objectWillChange has no effect

Tags:

swift

combine

I got this sample code about ObservableObject from Apple official website

import Foundation

class Contact: ObservableObject {
    @Published var name: String
    @Published var age: Int
    
    
    init(name: String, age: Int) {
        self.name = name
        self.age = age
    }
    
    func changeAge() -> Int {
        self.age += 1
        return self.age
    }
}



class Test {
    init() {
        let john = Contact(name: "John Appleseed", age: 24)
        _ = john.objectWillChange
            .sink { _ in
                print("\(john.age) will change")
        }
        print(john.changeAge())
    }
}

let test = Test()

When running on terminal by swift Contact.swift, the result is only 25, but official website shows the result should be

// Prints "24 will change"
// Prints "25"

Why the first line Prints "24 will change" is not shown?

Thank you.

like image 600
Shark Deng Avatar asked Mar 06 '26 10:03

Shark Deng


1 Answers

You have to store the AnyCancellable that's returned by sink, otherwise it cancels the subscription as soon as it's deinitialized when you assign to _.

In your simple example just assigning to a local variable is enough to get the printout that you want, because the variable still lives when you change the age:

let c = john.objectWillChange.sink {...}

But in a real app, you'd want to assign it to a property, which would keep the subscription for the duration that you need. Typically, it's done like this:

class Test {
    private var c: Set<AnyCancellable> = []
    init() {
        let john = Contact(name: "John Appleseed", age: 24)
        john.objectWillChange
            .sink { _ in
                print("\(john.age) will change")
            }
            .store(in: &c) // store here
        print(john.changeAge())
    }
}
like image 114
New Dev Avatar answered Mar 09 '26 00:03

New Dev



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!