【问题标题】:How to skip first item if got second on some time period on RxJava如果在 RxJava 上的某个时间段获得第二名,如何跳过第一项
【发布时间】:2020-04-17 11:30:51
【问题描述】:

我需要在收到事件后的 X 秒内执行一些操作(代表任何数据项 rxJava)。但如果在 X 秒结束前得到另一个事件,则需要在 X 秒内再次执行定时器重置和动作。

换句话说,我们有用户可以与之交互的 UI 元素。在用户不使用此 UI 元素 X 秒后,我们需要执行一些操作。 简单的解决方案可能如下所示:

Disposable disp;
void init() {
             final Flowable<Boolean> flowable = 
mapDragOrZoomSubject.delay(TIME_X, TimeUnit.SECONDS)
                    .toFlowable(BackpressureStrategy.DROP);
        disp = flowable. ...subscribeWith(ACTION);  // <-- action in X seconds of inactivity
    }

void gotNewUserInteraction() {
    disp.dispose();
    init();
}

如何在不基于一些 rxJava 操作符处理和重新创建 Flowable 的情况下做到这一点?

【问题讨论】:

    标签: rx-java rx-java2


    【解决方案1】:

    我对rxJava不太熟悉,但是你要找的操作符大概是debounce。所以也许是这样的:

    Disposable disp;
    void init() {
                 final Flowable<Boolean> flowable = 
    mapDragOrZoomSubject.delay(TIME_X, TimeUnit.SECONDS)
                        .toFlowable(BackpressureStrategy.DROP);
            disp = flowable
                     ...
                     .debounce(TIME_X, TimeUnit.SECONDS)
                     .subscribeWith(ACTION);  // <-- action in X seconds of inactivity
        }
    
    void gotNewUserInteraction() {
        disp.dispose();
        init();
    }
    

    【讨论】:

    • debounce() 是类似的事情,但是 debounce 正在做的是删除第一个值之后的所有后续值,例如:1,2,3 -> 1 我需要的是一些我需要的反向去抖只留下最新的动作(带有 X 秒计时器),所以它可能看起来像 1, 2, 3 -> 3
    • 我链接的文档说的有些不同。如果您查看文档中的 debounce 示例注释。它完全符合您的要求:1,2,3 -> 3
    • 对,真的,让我试试
    【解决方案2】:

    试试throttleWithTimeout(...) 运算符:

    @Test
    public void testThrottleWithTimeout()
    {
        Subject<String> eventSubject = PublishSubject.create();
        TestScheduler scheduler = new TestScheduler();
    
        TestObserver<String> observer = eventSubject
                .throttleWithTimeout( 1, TimeUnit.SECONDS, scheduler )
                .test();
    
        eventSubject.onNext( "foo" );
        scheduler.advanceTimeBy( 500, TimeUnit.MILLISECONDS );
        observer.assertNoValues();
    
        eventSubject.onNext( "bar" );
        scheduler.advanceTimeBy( 500, TimeUnit.MILLISECONDS );
        observer.assertNoValues();
    
        scheduler.advanceTimeBy( 500, TimeUnit.MILLISECONDS );
        observer.assertValue( "bar" );
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多