You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

SwiftUI:如何在子视图中仅创建一次非View对象

解决SwiftUI中仅在点击跳转时创建非View对象的问题

问题核心是当前代码里QuestionView会在HomeView首次渲染、以及highestNumber变化时重复初始化,导致Question被多次创建,不符合仅点击「Start」时创建一次的要求。要适配SwiftUI的声明式范式,关键是把非View对象的创建时机和视图跳转严格绑定,而不是依赖视图的初始化逻辑。

解决方案代码

修改HomeView:控制跳转时机与对象创建

struct HomeView: View {
    @State var highestNumber: Int = 12
    @State private var currentQuestion: Question?

    var body: some View {
        NavigationStack {
            Picker("Highest Number", selection: $highestNumber) {
                ForEach(4...12, id: \.self) { Text(String($0)) }
            }
            .pickerStyle(.wheel)
            
            Button("Start") {
                // 仅在点击Start时创建Question实例
                currentQuestion = Question(highestNumber)
            }
            // 只有currentQuestion非空时,才会触发跳转并初始化QuestionView
            .navigationDestination(item: $currentQuestion) { question in
                QuestionView(initialQuestion: question, highestNumber: highestNumber)
            }
        }
    }
}

修改QuestionView:接收已创建的对象

struct QuestionView: View {
    let highestNumber: Int
    @State private var currentQuestion: Question

    init(initialQuestion: Question, highestNumber: Int) {
        print("QuestionView.init")
        self.highestNumber = highestNumber
        self._currentQuestion = State(initialValue: initialQuestion)
    }

    var body: some View {
        Text(currentQuestion.prompt)
        Button("I got it") {
            // 仅在点击按钮时生成新问题
            currentQuestion = Question(highestNumber)
        }
    }
}

逻辑说明

  1. 严格控制对象创建时机:Question实例只会在「Start」按钮的点击闭包里创建,完全和用户操作绑定,避免了视图渲染时的意外初始化。
  2. 用状态驱动跳转:通过navigationDestination(item:)关联currentQuestion状态,只有当该状态被设置(用户点击Start)时,才会初始化QuestionView并传递已创建好的Question。
  3. 移除不必要的绑定:QuestionView不再接收highestNumber的绑定,而是接收初始值用于后续生成新问题,避免了外部状态变化触发视图重新初始化。

这样就能彻底解决Question重复创建的问题,同时符合SwiftUI声明式的状态驱动思维。

内容的提问来源于stack exchange,提问作者pquimo

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.03 01:00:58