# 策展 · X (Twitter) 🔥

> 作者：Flo writes Code (@FloWritesCode) · 平台：X (Twitter) · 日期：2026-03-31

> 原始來源：https://x.com/FloWritesCode/article/2038609301258809373

## 中文摘要

# 停止使用 ObservableObject

> ObservableObject 會引入副作用和效能問題，但有替代方案。

ObservableObject 曾經是為 SwiftUI View 建構 ViewModels 和其他 data sources 的「唯一」解決方案。多年來，主要問題是該使用哪種 PropertyWrapper：ObservedObject、StateObject 還是 EnvironmentObject。無論您選擇哪種方法，它們都依賴於 Combine 進行 View updates——您的 ObservableObject 會有一個 objectWillChangeobject，其型別為 ObjectWillChangePublisher，用於通知 View 任何 @.Published 屬性變更。

## 問題所在

一如往常，魔鬼藏在細節裡：這個 publisher 每次都會在任何 published 屬性變更時觸發——無論 View 是否依賴於該屬性。在許多簡單的使用情境中，這可能不重要。但一旦您將 View 分解成更小的 Subviews，或開始在多個 View 之間共享 ObservableObject，事情就會開始變得棘手：如果 View 不必要地重繪，就會出現明顯的效能問題。所有這些都發生了，因為 ObservableObject 是透過 Combine framework 建構（並連接到您的 View）的。

## 解決方案

首先：如果您的 app 需要支援 iOS 17 之前的版本（或嚴重依賴於 Combine pipelines 來處理您的 published properties），您可以停止閱讀這篇文章，因為我們即將探討的 framework 就是在那個時候引入的。它叫做 Observation，是 ObservableObject 的（幾乎）直接繼承者。這個 framework 包含一個新的 @.Observable macro，您可以將其附加到 Swift class。

```swift
// Old approach
import SwiftUI

class ViewModel: ObservableObject {
  @Published var username: String = ""
}

// New approach
import SwiftUI
import Observation

@Observable
class ViewModel {
  var username: String = ""
}
```

如果您對細節很敏銳，您會注意到一個根本性變革：Implicit State。過去您需要明確標記屬性為 @.Published。任何未標記的屬性都不會更新 View。但有了 Observation，任何屬性都會更新。您可以透過附加 @.ObservationIgnored macro 將屬性標記為不更新。

我在本文開頭討論了不同的 PropertyWrappers，用於將 ObservableObject 附加到 View。這些不適用於 @.Observable class。相反地，您將只使用 @.State 來處理此 View 所擁有的 class，以及使用 @.Bindable 或 @.Environment 來處理另一個 View 所擁有的 class。

## 標籤

SwiftUI, 教學資源, iOS, Apple
