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

Swift Combine数组映射报错:闭包传入不接受闭包的KeyPath参数

Combine中数组映射的编译错误解决

问题代码

Provider类代码

func getUserPosts(userID: String) -> AnyPublisher<[PostDTO], NetworkErrors> {
    let url = URL(string: "https://jsonplaceholder.typicode.com/posts?userId=\(userID)")
            return AF.request(url!,method: .get)
                         .publishDecodable(type: [PostDTO].self)
                         .value()
                         .mapError { _ in NetworkErrors.decoderError }
                         .eraseToAnyPublisher()
}

Interactor类映射代码(存在错误)

func getUserPosts(userID: String) -> AnyPublisher<[Post], NetworkErrors> {
    postListRemoteProvider.getUserPosts(userID: userID).map {
        Post(id: $0.id, title: $0.title, detail: $0.body, isFavorite: false)
    }.eraseToAnyPublisher()
}

错误信息

Trailing closure passed to parameter of type 'KeyPath<[PostDTO], [Post]>' that does not accept a closure

错误原因

上游Publisher输出的是[PostDTO]数组类型,当前代码直接在Combine的map闭包里尝试用整个数组($0)初始化单个Post,属于类型不匹配。同时Swift为集合类型的map提供了KeyPath重载,编译器误以为你要传入KeyPath而非闭包,因此抛出该错误。

解决方案

需要在Combine的map操作中,对上游输出的数组执行Swift数组的map遍历,将每个PostDTO转换为Post实例:

修正后的代码

func getUserPosts(userID: String) -> AnyPublisher<[Post], NetworkErrors> {
    postListRemoteProvider.getUserPosts(userID: userID)
        .map { postDTOs in
            postDTOs.map { dto in
                Post(id: dto.id, title: dto.title, detail: dto.body, isFavorite: false)
            }
        }
        .eraseToAnyPublisher()
}

简化写法

func getUserPosts(userID: String) -> AnyPublisher<[Post], NetworkErrors> {
    postListRemoteProvider.getUserPosts(userID: userID)
        .map { $0.map { Post(id: $0.id, title: $0.title, detail: $0.body, isFavorite: false) } }
        .eraseToAnyPublisher()
}

外层的map是Combine Publisher的操作,负责接收上游的[PostDTO]数组;内层的map是Swift数组的遍历方法,负责将数组中的每个PostDTO转换为Post,最终得到[Post]数组作为新的Publisher输出。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.10 22:22:16