Browse Questions

Answer: Yes — passing an observed property as inout always calls both willSet and didSet, even if the function never modifies the value.

Code Example:

var score = 10 {
    willSet { print("willSet \(newValue)") }
    didSet  { print("didSet \(oldValue) -> \(score)") }
}

func doNothing(_ value: inout Int) { }

doNothing(&score)
// willSet 10
// didSet 10 -> 10

Why: inout uses copy-in copy-out semantics: the value is copied into the function, and when the function returns the (possibly unchanged) value is written back to the original property. That write-back is a normal set, so observers run.

Key Points:

  • The observers fire once, at the end of the call — not for each modification inside the function.
  • Mutating methods on a struct property behave the same way (items.append(x) is effectively an inout mutation of items).