Swift,在航班上合并、取消并替换为新的请求运营商

Swift, Combine, cancel on the flight and replace with the new request operator

我接到了这个获取图片的网络电话。

func load() {
        guard let url = URL(string: urlString)
        else { return }

        subscription = URLSession.shared.dataTaskPublisher(for: url)
            .map({ UIImage(data: [=11=].data) })
            .replaceError(with: nil)
            .receive(on: RunLoop.main)
            .sink(receiveValue: { [weak self] in self?.image = [=11=] })
    }

这是由正在填充的文本字段触发的。输入每个字母后,我希望我的发布者等待执行,比方说 2 秒,除非用户输入另一个字母。如果发生这种情况,我希望计时器再次重置为 2 秒。

如果同时发送了新请求,是否有即时取消运算符?

感谢大家的帮助。

这是使用反应式库做的一件非常标准的事情,而且很容易完成。 switchToLatest 运算符是一个神奇的运算符。

@available(iOS 14.0, *)
final class ViewController: UIViewController {
    var textField: UITextField!
    var image: UIImage?
    var cancelBag = Set<AnyCancellable>()

    override func viewDidLoad() {
        super.viewDidLoad()

        textField.textPublisher // this is from the `CombineCocoa` library
            .debounce(for: 2, scheduler: RunLoop.main)
            .compactMap { makeURL(from: [=10=]) }
            .map {
                URLSession.shared.dataTaskPublisher(for: [=10=])
                    .catch { _ in Empty() } // what do you want to do with loading errors?
            }
            .switchToLatest()
            .map { UIImage(data: [=10=].data) }
            .receive(on: RunLoop.main)
            .sink(receiveValue: { [weak self] in self?.image = [=10=] })
            .store(in: &cancelBag)
    }
}

func makeURL(from: String?) -> URL? {
    // build and return the correct URL for the image request
    fatalError()
}