无法推断通用参数"输出"

  • 本文关键字:参数 输出 swift combine
  • 更新时间 :
  • 英文 :


当我在Just{}中添加print("value == (value)")时,我得到一个编译错误:

无法推断通用参数'Output'

我代码:

import Foundation
import Combine
class JustViewObservableObject: ObservableObject {

var cancellable: AnyCancellable?

struct Student: Decodable {
let name: String
}

let json = """
[{
"name": "李雷"
}]
"""
init() {
let publisher = PassthroughSubject<String, Never>()
publisher.flatMap { value -> Just in
print("value == (value)")
return Just(value.data(using: .utf8)!)
.decode(type: [Student].self, decoder: JSONDecoder())
.catch { _ in
Just([Student(name: "无名氏")])
}
}
publisher.send(json)
}
}

需要将闭包签名中的Just替换为返回类型的全称,即此表达式的类型:

Just(value.data(using: .utf8)!)
.decode(type: [Student].self, decoder: JSONDecoder())
.catch { _ in
Just([Student(name: "无名氏")])
}

因为你的闭包在添加print语句后有多条语句,Swift拒绝推断它的返回类型。

但是,由于这里使用了相当多的组合操作符,因此完整类型相当长:

Publishers.ReplaceError<Publishers.Decode<Just<JSONDecoder.Input>, [JustViewObservableObject.Student], JSONDecoder>>

使用eraseToAnyPublisher会更实用,这样类型就变成了AnyPublisher<[Student], Never>。您还可以将.catch { _ in Just(...) }替换为replaceError(with:)(注意一个小区别是,如果使用replaceError,则会立即创建Student对象,但我认为这无关紧要,除非您的实际代码不同):

publisher.flatMap { value -> AnyPublisher<[Student], Never> in
print("value == (value)")
return Just(value.data(using: .utf8)!)
.decode(type: [Student].self, decoder: JSONDecoder())
.replaceError(with: [Student(name: "无名氏")])
.eraseToAnyPublisher()
}

就我个人而言,我不认为用Combine进行解码有什么意义。我会使用do...catch:

publisher.map { value -> [Student] in
print("value == (value)")
do {
return try JSONDecoder().decode([Student].self, from: value.data(using: .utf8)!)
} catch {
return [Student(name: "无名氏")]
}
}

最新更新