面试题答案
一键面试- 利用Combine框架管理异步数据流:
- 创建Publisher:对于每个网络API调用,使用
URLSession
的dataTaskPublisher
(或其他合适的Publisher创建方式)来创建Publisher
。例如:
let url = URL(string: "https://example.com/api")! let dataPublisher = URLSession.shared.dataTaskPublisher(for: url)
- 处理依赖关系:使用
flatMap
操作符来处理API调用的依赖关系。如果API2依赖API1的返回数据,那么可以这样写:
let api1Publisher = URLSession.shared.dataTaskPublisher(for: api1URL) .map(\.data) .decode(type: API1Response.self, decoder: JSONDecoder()) let api2Publisher = api1Publisher.flatMap { api1Data in let api2URL = createAPI2URL(from: api1Data) return URLSession.shared.dataTaskPublisher(for: api2URL) .map(\.data) .decode(type: API2Response.self, decoder: JSONDecoder()) }
- 创建Publisher:对于每个网络API调用,使用
- 可能用到的操作符:
- map:用于将
Publisher
发出的数据转换为另一种类型。例如将(data: Data, response: URLResponse)
转换为具体的模型对象,如map(\.data).decode(type: MyModel.self, decoder: JSONDecoder())
。 - decode:专门用于将
Data
解码为特定的模型类型。 - flatMap:如上述处理API依赖关系时,将一个
Publisher
发出的数据作为输入,创建并返回另一个Publisher
。 - catch:用于捕获
Publisher
发出的错误,并提供一个备用的Publisher
或者进行错误处理。例如:
api2Publisher.catch { error in // 处理错误,返回一个备用Publisher return Just(API2Response.defaultValue) }
- map:用于将
- SwiftUI视图响应数据流变化:
- 在SwiftUI视图中,可以使用
@StateObject
或@ObservedObject
来观察ObservableObject
类型的视图模型。 - 视图模型中定义一个
Published
属性来存储处理后的数据流结果。例如:
class MyViewModel: ObservableObject { @Published var finalData: [MyFinalModel] = [] init() { let finalPublisher = api2Publisher .map { api2Data in // 对api2Data进行一系列转换处理得到MyFinalModel数组 return convertAPI2DataToFinalModel(api2Data) } finalPublisher .assign(to: \.finalData, on: self) .store(in: &cancellables) } private var cancellables = Set<AnyCancellable>() }
- 在SwiftUI视图中使用:
当struct MyView: View { @StateObject var viewModel = MyViewModel() var body: some View { List(viewModel.finalData) { data in // 展示数据 Text(data.description) } } }
viewModel.finalData
发生变化时,SwiftUI视图会自动重新渲染,展示最新的数据。 - 在SwiftUI视图中,可以使用