Large structs and stack overflow

Property Wrapper is also useful.

@propertyWrapper
struct CopyOnWriteBox<Value> {

    private var ref: Ref<Value>

    init(wrappedValue: Value) {
        self.ref = Ref(wrappedValue)
    }

    var wrappedValue: Value {
        get {
            ref.value
        }
        set {
            if isKnownUniquelyReferenced(&ref) {
                ref.value = newValue
            } else {
                ref = Ref(newValue)
            }
        }
    }

    private final class Ref<T> {
        var value: T

        init(_ value: T) {
            self.value = value
        }
    }
}

extension CopyOnWriteBox: Equatable where Value: Equatable {
    static func == (lhs: Self<Value>, rhs: Self<Value>) -> Bool {
        lhs.ref.value == rhs.ref.value
    }
}
struct Person: Equatable {
    var name: String
}

struct Team: Equatable {
    @CopyOnWriteBox
    var leader: Person
}

var t1 = Team(leader: Person(name: "aaa"))
t1.leader.name = "bbb"
12 Likes