SwiftUI:嵌套数组场景下ForEach动态生成列表的问题
解决嵌套数组Fleet模型的视图展示与导航数据传递问题
问题根源
HourlyRates中的year、foHourlyRate、captHourlyRate均为数组类型,原代码直接将数组传入Text会引发类型不匹配错误- 未处理数组元素的一一对应关系,无法按年份关联展示对应费率
- 导航时可能未正确传递完整
Fleet对象到子视图
解决方案
1. 新增辅助模型统一单年份费率数据
为清晰处理年份与费率的对应关系,新增YearRate模型封装单一年份的费率信息:
struct YearRate: Identifiable { let id = UUID() let year: Int let foHourlyRate: Double let captHourlyRate: Double }
在HourlyRates中添加计算属性,将三个数组转换为[YearRate](需确保三个数组长度一致):
struct HourlyRates: Identifiable { let id: UUID var year: [Int] var foHourlyRate: [Double] var captHourlyRate: [Double] // 转换为单年份费率数组 var yearRates: [YearRate] { guard year.count == foHourlyRate.count, year.count == captHourlyRate.count else { return [] // 长度不一致时返回空数组,可按需添加错误提示 } return zip(zip(year, foHourlyRate), captHourlyRate).map { YearRate(year: $0.0, foHourlyRate: $0.1, captHourlyRate: $1) } } }
2. 修复RateCardView的展示逻辑
修改视图遍历逻辑,基于转换后的yearRates数组展示单年份费率:
struct RateCardView: View { var fleet: Fleet var body: some View { List { // 展示机型名称 Text(fleet.fleetName) .font(.title) .fontWeight(.bold) // 遍历每一组费率下的年份数据 ForEach(fleet.rates) { hourlyRate in Section(header: Text("费率组")) { ForEach(hourlyRate.yearRates) { yearRate in HStack { Text("Year \(yearRate.year)") Spacer() Text(String(format: "%.2f", yearRate.foHourlyRate)) Spacer() Text(String(format: "%.2f", yearRate.captHourlyRate)) } } } } } } }
3. 确保导航数据传递正确
在父视图PayRateView中,通过NavigationLink正确传递Fleet对象到子视图:
struct PayRateView: View { var fleets: [Fleet] // 父视图持有Fleet数组 var body: some View { NavigationStack { List(fleets) { fleet in NavigationLink(destination: RateDetailView(fleet: fleet)) { Text(fleet.fleetName) } } .navigationTitle("机型费率") } } } // 子视图RateDetailView,内部调用RateCardView struct RateDetailView: View { var fleet: Fleet var body: some View { RateCardView(fleet: fleet) .navigationTitle(fleet.fleetName) } }
额外说明
- 若
HourlyRates的三个数组长度可能不一致,建议在数据初始化阶段做校验,避免展示异常 - 可根据需求调整
Text的格式化规则(比如添加货币符号) - 若无需保留原数组结构,可直接修改
HourlyRates模型,直接存储[YearRate]以减少转换步骤
内容的提问来源于stack exchange,提问作者weekendwarrior
相关产品推荐
相关产品推荐

