RxSwift,如何应用背压为 Stream 中的每个项目连续显示 UIAlertView

RxSwift, How to apply back-pressure to serially display a UIAlertView for each item in a Stream

我有一个 Observable<Item> 异步发出一系列项目。对于流中的每个项目,我需要显示一个 UIAlertView。每次用户关闭警报(如果有新项目)时,我需要获取下一个项目并为其显示新警报。

我遇到的问题是 Observable 发射项目的速度太快了。显示警报时,会发出多个项目,我丢失了该信息。

流可能在一秒钟内产生 10 个项目,我想显示 10 个弹出窗口,它们将依次打开,一次一个,一个接一个地打开。

有没有一种方法可以在我准备好显示警报后才使用流中的下一个项目?

你可以这样做

获取 2 个 Observable:

  1. 您现有的 Observable 发出您在回答中描述的值。
  2. 一个 Observable,它在用户关闭警报视图时发出一个值。

然后使用 zip 组合运算符从这 2 个 Observable 中创建第三个 Observable。由于 zip 运算符,第三个 Observable 仅在 Observable 1 和 Observable 2 都发出一个值时发出一个值。换句话说,当您的流中有事件并且用户取消了先前的警报时,它会发出一个值。每当第三个(压缩的)Observable 发出一个值时,你就会显示一个警报。

这是一张关于 zip 运算符如何工作的图片(从神话般的 RxMarbles 中偷来的):

在此图片中,第一行 是您的信息流。 第二行 是用户关闭警报视图。 第三行 是显示下一个警报的信号。

您可以看到,虽然显示警报 (1A),但您的流中还发出了另外两个值((2)(3))。压缩会注意第三行的下一个事件仅在用户关闭警报时发出 (B)。然后压缩 "grabs" 流中的下一个事件并在第三行发出 (2B) 。这会导致显示下一个警报。

要完成这项工作,您必须通过一个事件 (A) 启动 "alert dismissed" Observable。因为否则 zip 将在触发第一个事件之前等待第一个警报被解除。

在代码中它看起来像这样。 (我只是使用 Observable<Int> 来模拟您的流)。 didDismissedAlert Observable 的类型是 Observable<Void>:

Observable.zip(stream, didDismissAlert.startWith(())) { (streamValue, _) -> Int in
        return streamValue
    }
    .subscribe(onNext: { streamValue in
        // showAlert with the value from the stream
    })
    .disposed(by: disposeBag)