我必须制作一个在我的情况为真时重试Observable的方法。我像这样通过闭包传递条件:
Observable.retrySource {$ 0!= 20}
我的函数必须使用通用参数,例如map,flatMap ...
扩展名ObservableType {
func retrySource<T: Error>(closure: @escaping (T) -> Bool) -> Observable<E> {
return retryWhen { (error: Observable<T>) in
return error
.flatMap { value -> Observable<Void> in
guard closure(value) else {
return .error(error as! Error)
}
return Observable.just(Void())
}
}
}
} 而且,我不知道 1)如何检查我的病情? 2)如何将封闭中的Observable传递给func?
我的可观察物:
numberButton.rx.tap
.flatMapLatest { return randomInt }
.retrySource { $0 != 5 }
.subscribe(onNext: { print($0) },
onError: { error in
print(error)
}, onCompleted: {
print("finish")
})
.disposed(by: disposeBag)
}
答案 0 :(得分:1)
如果我了解您想要的内容,这应该可以工作,但不适用于您发布的示例代码。那将重新订阅完全没有任何意义的按钮。
请以以下示例尝试:
numberButton.rx.tap
.flatMapLatest {
randomProducer(0..<6) // random int
.asObservable()
.retrySource { $0 != 5 } // but can't equal 5
}
.subscribe(onNext: { print($0) },
onError: { print($0) },
onCompleted: { print("finish") })
.disposed(by: bag)
代码如下:
extension ObservableType {
func retrySource(_ pred: @escaping (E) -> Bool) -> Observable<E> {
return map { element in
guard pred(element) else { throw RetrySourceError() }
return element
}
.retryWhen { error in
error.map {
guard $0 is RetrySourceError else { throw $0 }
}
}
}
}
struct RetrySourceError: Error { }
它是如何工作的:如果谓词为true,则它只是传递事件。如果谓词为假,则抛出错误,并且一旦抛出的错误为.retryWhen
,RetrySourceError
都会导致重试。任何其他类型的错误都将被传递。
这是我制作随机数的方式:
func randomProducer(_ range: Range<Int>) -> Single<Int> {
return Single.create {
$0(.success(Int.random(in: range)))
return Disposables.create()
}
}