Swift private(set)访问控制
Swift private(set)访问控制

Swift private(set)访问控制

Swift中的private(set) 是一种访问控制的声明,表示属性可以被外部读取,但只能在定义它的作用域内修改。这是一种保护机制,常用于保证数据的完整性和安全性。

@Observable
class ViewModel {
    private(set) var locations = [Location]()
    var selectedPlace: Location?
}

private(set) 的作用

限制写权限:locations 的值只能在定义它的作用域(通常是当前类或结构体)内被修改。

允许读权限:外部仍然可以通过 viewModel.locations 访问和读取它的值,但无法直接修改。

class ViewModel {
    private(set) var locations = [Location]()
    
    func addLocation(_ location: Location) {
        locations.append(location) // 内部可以修改
    }
}

let viewModel = ViewModel()
print(viewModel.locations) // 外部可以读取

// viewModel.locations.append(Location(...)) // 外部不能直接修改

为什么使用 private(set)?

1、保护数据完整性

让外部代码无法随意更改数据,避免意外或恶意的修改。

只允许通过类或结构体中定义的方法来修改数据,这样可以确保修改时符合业务逻辑。

例子

class BankAccount {
    private(set) var balance = 0
    
    func deposit(amount: Int) {
        guard amount > 0 else { return }
        balance += amount
    }
}

let account = BankAccount()
account.deposit(amount: 100)
print(account.balance) //  100
// account.balance = 200 //  不允许直接赋值

2、清晰的接口设计

外部代码只能读取 locations,修改逻辑由 ViewModel 自己管理。这使得接口更加清晰,减少了误用的可能性。

3、便于调试和维护

当数据只能通过受控的方法修改时,更容易在代码中跟踪数据的变化来源。

private(set) vs 完全 private

1、private:

属性既不能被外部读取,也不能被外部修改。

使用场景:完全隐藏内部实现细节。

2、private(set):

属性可以被外部读取,但不能被外部修改。

使用场景:需要外部访问数据,但不希望外部修改数据。

总结

private(set) 是一种限定写权限的修饰符,用于在保持外部可访问性的同时保护数据不被随意修改。这种模式在 Swift 的 MVVM 架构中非常常见,因为它允许 View 层读取数据,但确保所有的数据更新只能通过 ViewModel 的方法进行,从而维护了逻辑的集中性和一致性。

如果您认为这篇文章给您带来了帮助,您可以在此通过支付宝或者微信打赏网站开放者。

发表回复

您的电子邮箱地址不会被公开。 必填项已用 * 标注