web-dev-qa-db-ja.com

rxjavaを使用してAndroidの遅延後にメソッドを呼び出す方法は?

HandlerメソッドをRxJavaに置き換えようとしています。
私の要件:

5秒後にのみgetTransactionDetails()メソッドを呼び出したい。

これはハンドラを使用した私の作業コード:

new Handler().postDelayed(new Runnable() {
      @Override
      public void run() {
        getTransactionDetails();
      }
    }, 5000); 

Rx Javaコード-動作していません:

Observable.empty().delay(5000, TimeUnit.MILLISECONDS)
        .subscribeOn(Schedulers.io())
        .observeOn(AndroidSchedulers.mainThread())
        .doOnNext(o -> getTransactionDetails())
        .subscribe();
31
Vibindas M

doOnNext() は副作用用です。ロギングはデータの流れを変更しないため、たとえばロギングの目的で使用できます。ただし、getTransactionDetails()の結果を渡す必要があるため、代わりにmapを使用する必要があります。

第二に、 Observable.empty() 完了/破棄メッセージを伝播するObservableを作成します。これはdoOnNext()map()もトリガーしません。代わりに Observable.just() を使用してこれを修正できますが、より慣用的な方法は Observable.timer() を使用することです。

Observable.timer(5000, TimeUnit.MILLISECONDS)
        .map(o -> getTransactionDetails())
        .observeOn(AndroidSchedulers.mainThread())
        .subscribe( ... );

スケジューラに関する最後の注意。 Observable.timer()delay()はデフォルトで計算スケジューラーで実行されるため、メインスレッドの外部で.subscribeOn(Schedulers.io())を実行するためにgetTransactionDetails()を呼び出す必要はありません。これを制御する場合、Observable.timer()およびdelay()は、パラメーターとしてSchedulerを取ることができます。したがって、UIスレッドで.observeOn(AndroidSchedulers.mainThread())の結果を使用する場合は、getTransactionDetails()を呼び出す必要があります。 observeOn()の後のすべての演算子は、定義されたSchedulerで実行されるため、計算後にobserveOn()を配置する必要があります。

Edit:もちろん、これはgetTransactionDetails()の結果を気にする場合です。そうでない場合は、クライドの回答を参照してください。

41
Geoffrey Marizy
Observable
     .timer( 5000, TimeUnit.MILLISECONDS )
     .subscribeOn(Schedulers.io())
     .map(o -> getTransactionDetails() )
     .subscribe();

サブスクライブが空なので、observeOnは必要ありません。タイマーを使用すると、より正確な方法になります

13
Sergey Buzin

delay()は出力する必要があるため機能しませんが、empty()は実際には何も出力しません。

代わりに、Observable.timer()を使用する必要があります。

9
xizzhu

これを試して

Observable.just(true).delay(5000, TimeUnit.MILLISECONDS)
    .subscribeOn(Schedulers.io())
    .observeOn(AndroidSchedulers.mainThread())
    .map(o -> getTransactionDetails())
    .subscribe();
1
Mr. Zahid

すでにサブスクリプションを遅延 定義済み 。あなたの例はこの方法で実装できます:

getTransactionDetails().delaySubscription(5000, TimeUnit.MILLISECONDS)
0
Sergey

ビューで使用できるディスポーザブルが必要な場合、Completable Completableを使用すると、ソースCompletableのいずれかが(通常またはエラーで)終了するとすぐに終了し、他のすべてのCompletableをキャンセルするオブジェクトが返されます。

例:

Completable.timer(5, TimeUnit.SECONDS, AndroidSchedulers.mainThread())
            .subscribe(() -> {
                // code after delay here
            });

サービスを完了するには、サブスクリプションをお勧めします

例:

observable.timer(5000, TimeUnit.MILLISECONDS)
    .map(o -> {
              // your code after delay here
              })
    .observeOn(AndroidSchedulers.mainThread())
    .subscribe( ()-<{
                   // enter the service here
                } );
0