惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

T
Threatpost
Exploit-DB.com RSS Feed
Exploit-DB.com RSS Feed
S
Security Affairs
N
News and Events Feed by Topic
T
Tenable Blog
P
Proofpoint News Feed
W
WeLiveSecurity
Simon Willison's Weblog
Simon Willison's Weblog
Google DeepMind News
Google DeepMind News
C
CERT Recently Published Vulnerability Notes
Help Net Security
Help Net Security
I
Intezer
T
Threat Research - Cisco Blogs
S
Secure Thoughts
C
Cyber Attacks, Cyber Crime and Cyber Security
L
Lohrmann on Cybersecurity
AWS News Blog
AWS News Blog
Google Online Security Blog
Google Online Security Blog
cs.AI updates on arXiv.org
cs.AI updates on arXiv.org
Know Your Adversary
Know Your Adversary
Project Zero
Project Zero
The Hacker News
The Hacker News
Security Archives - TechRepublic
Security Archives - TechRepublic
T
Tor Project blog
N
News | PayPal Newsroom
cs.CL updates on arXiv.org
cs.CL updates on arXiv.org
Hacker News - Newest:
Hacker News - Newest: "LLM"
A
Arctic Wolf
Forbes - Security
Forbes - Security
O
OpenAI News
K
KPMG report finds enterprise disconnect between AI and its ROI | CIO
Security Latest
Security Latest
P
Palo Alto Networks Blog
S
Schneier on Security
S
Securelist
C
Cybersecurity and Infrastructure Security Agency CISA
H
Heimdal Security Blog
V
Vulnerabilities – Threatpost
www.infosecurity-magazine.com
www.infosecurity-magazine.com
博客园_首页
T
Troy Hunt's Blog
Latest news
Latest news
Recent Announcements
Recent Announcements
MyScale Blog
MyScale Blog
人人都是产品经理
人人都是产品经理
L
LINUX DO - 热门话题
M
MIT News - Artificial intelligence
N
Netflix TechBlog - Medium
V
Visual Studio Blog
H
Hacker News: Front Page

肘子的 Swift 记事本 | Fatbobman's Blog

当每一次写入都有了新价格 -- 肘子的 Swift 周报 #144 当 Linux 成为“空气”:容器、Agent 与不再重要的“桌面之争” -- 肘子的 Swift 周报 #143 两个 SwiftUI 动画 Bug 排查小记 SPI 加入 Apple,Swift 迈向自举 -- 肘子的 Swift 周报 #142 Swift 还让你 Excited 吗? -- 肘子的 Swift 周报 #141 从 Size Class 到可用空间,horizontalSizeClass 还可靠吗? WWDC 26:AI 帮你看完了,然后呢? -- 肘子的 Swift 周报 #140 WWDC 2026 初印象:符合预期,但更务实 -- 肘子的 Swift 周报 #139 Core Data + Observation:从属性级响应到心智解放 稳定 > 新功能 -- 肘子的 Swift 周报 #138 用自定义 Layout 化解 SwiftUI List 的行高与间距跳变 从社区路标到生态基石:Dave Verwer 的新篇章 -- 肘子的 Swift 周报 #137 消失的 WWDC 愿望单 -- 肘子的 Swift 周报 #136 CocoaPods 正在退场,SwiftPM 才刚到第二章 -- 肘子的 Swift 周报 #135 让 AI 从称手到称心 -- 肘子的 Swift 周报 #134 Swift 并发正被更广泛地接纳 -- 肘子的 Swift 周报 #133 从 OpenSwiftUI 到 DanceUI:换个方式 Dive SwiftUI -- 肘子的 Swift 周报 #132 被 Vibe 摧毁的版权壁垒,与开发者的新护城河 -- 肘子的 Swift 周报 #131 苹果的罕见妥协:当高危漏洞遇上“拒升”潮 -- 肘子的 Swift 周报 #130 一墙之隔,不同的时空 -- 肘子的 Swift 周报 #129 我的 App 审核被卡了? -- 肘子的 Swift 周报 #128 CDE:一次让 Core Data 更像现代 Swift 的尝试 50 岁的苹果和 51 岁的我 -- 肘子的 Swift 周报 #127 2026 年,为什么我仍在思考 Core Data Macbook Neo:苹果重回校园的起点 -- 肘子的 Swift 周报 #126 跨域传递 NSManagedObjectContext 为什么在 Swift 6.2 中不再报错?真正的变化不在编译器 Xcode 26.3 + Claude Agent:模型替换、MCP、Skill 与自适应配置 macOS 录屏软件开发实录:从像素抓取到元数据重现 isolated(any) 与 #isolation:让 Swift 闭包自动继承隔离域 在 tvOS 上活下來:一個非典型播放器的工程實錄 告别“可移植汇编”:我已让 Swift 在 MCU 上运行七年 独立开发者的试炼:Zipic 从 0 到 1 的产品化之路 逃离 Mac App Store:如何从零构建独立应用的分发与售卖体系 Partytown 实战:修复 GTM 自定义事件与 dataLayer 失效问题 Swift 6 编译加速:启用 Swift-Syntax 预构建 (Prebuilts) Swift 模块化:使用 package 关键字实现 Target 间安全共享 Monorepo 实战:解决 VSCode/Cursor 中 SwiftLint 配置失效问题 VSCode/Cursor 测试 Core Data:手动编译 xcdatamodeld 指南
为什么父视图无法修改子视图的 @State
东坡肘子 · 2025-12-18 · via 肘子的 Swift 记事本 | Fatbobman's Blog

核心摘要@State 旨在管理视图的内部私有状态,其初始值仅在视图 第一次建立标识(Identity) 时生效;若需持续响应外部数据的变化,请使用 @Binding 或普通的 let 属性。

问题现象

很多 SwiftUI 初学者经常会遇到这样一个“奇怪”的现象:

一个子视图包含两个参数,一个使用 @State 修饰,另一个没有。在父视图中更新这两个参数对应的数据源时,只有没有标注 @State 的属性会随之更新,而标注了 @State 的属性则“无动于衷”。

struct SubView: View {
    let normalValue: String
    @State var stateValue: String // 父视图更新时,这里不会变
    
    // ...
}

@State 的核心语义

SwiftUI 作为一个声明式响应框架,@State 是其最基础的状态管理工具。它的核心语义只有一条:

由 SwiftUI 运行时负责存储和管理内存,确保由 @State 持有的值,其生命周期与视图的生命周期(Identity)完全一致。

这意味着 @State 显式地定义了一个“私域”属性。一旦视图被分配了存储空间,该属性就由视图内部全权接管。

@State var name = "abc"
// 语义上等同于
@State private var name = "abc"

因此,苹果官方文档和最佳实践都强烈建议将 @State 声明为 private,以强化这一概念:这是视图的私有财产,不应由外部干涉。

为什么父视图无法修改它?

为了贯彻 @State 的语义,SwiftUI 在底层实现中采用了类似“一次性初始化”的策略。

  1. 首次创建:当视图第一次被加载到视图树中(建立 Identity)时,SwiftUI 会根据构造函数(init)中传入的参数,初始化 @State 的内部存储(State<T>)。
  2. 后续更新:当父视图刷新并重新调用子视图的 init 方法时,虽然传入了新的参数值,但 SwiftUI 检测到该视图的存储已经存在。为了保持状态的连续性(即防止用户输入的内容丢失),SwiftUI 会直接忽略 init 中传入的新值,继续使用内部存储中现有的值。

简单来说,@State 就像一个只在搬新家时才接受礼物的盒子,之后的每一次拜访,它都会拒绝接收新的礼物,以保护盒子里已有的东西。

扩展阅读:如果你对底层实现感兴趣,可以深入了解 DynamicProperty 协议@State 在内部维护了一个状态枚举,只有在特定的初始化阶段才会接受外部赋值。

解决方案与实践总结

  1. 区分数据源

    • 如果数据由父视图拥有并控制,子视图只负责展示,请使用普通的 let 属性。
    • 如果子视图需要修改这份数据并同步回父视图,请使用 @Binding
    • 只有当数据是子视图完全私有的内部状态(如按钮的高亮状态、输入框的临时内容)时,才使用 @State
  2. 强制刷新(不推荐)

    • 如果确实需要重置 @State,可以通过改变视图的 id.id(value))来强制 SwiftUI 销毁并重建视图,从而触发新的初始化流程。但这会带来性能开销和状态丢失。
  3. 引用类型的新选择

    • 从 iOS 17 起,配合 Observation 框架,@State 取代 @StateObject 用于持有 Observable 对象。
    • ⚠️ 注意性能:与 @StateObject 不同,@State 不具备懒加载(Lazy Initialization)机制。请避免在 View 的 init 或属性默认值中直接初始化开销巨大的引用类型对象,否则每次视图重绘都会导致对象被重复创建(尽管之后会被立即丢弃)。在确实需要使用懒加载的场景,可以通过自定义 @LazyState 来应对
// ❌ 避免这样做,HeavyObject 会被重复创建
@State private var store = HeavyObject() 
   
// ✅ 推荐:在 onAppear 中或使用 lazy 模式初始化

相关提示

订阅 Fatbobman 周报

每周精选 Swift 与 SwiftUI 开发技巧,加入众多开发者的行列。

立即订阅