我有一个带回调的异步方法UserControl
。它从我的应用程序的不同类中多次调用。我需要这个电话一个接一个地开始,而不是同时开始。
我想用Rx实现它。像这样:
makeRequest()
但是现在所有请求都是并行的。我需要在这里添加什么来逐个运行请求?
答案 0 :(得分:1)
根据评论,您在这里分开了流和请求。执行请求的每个客户端都期望来自请求的结果。但是没有允许并行运行的请求,在这种情况下,我认为最简单的方法是将Scheduler
限制为应用程序全局后台顺序线程执行程序,即:
Schedulers.from(Executors.newSingleThreadExecutor())
在你的应用程序的某个地方提供这个单线程Executor,当然,每个请求流将使用相同的对象,这是非常重要的:
private final Scheduler singleThreadScheduler = Schedulers.from(Executors.newSingleThreadExecutor());
public void execute() { // This method called many times from another classes
Observable.just(true)
.map(o -> {
internalExecute();
return o;
})
.subscribeOn(singleThreadScheduler)
.subscribe();
}
private void internalExecute() { // This method should called only when previous call was finished
makeRequest(this::onRequestFinished);
}
private void onRequestFinished() {
//NOTE: you should make sure that the callback execute where you need it (main thread?)
// here is I handle request finish
}
除此之外,您不会向客户端公开Observable
,而是使用回调机制,您可以通过execute()
返回Observable
来进一步利用被动方法。 (并享受Obesrvable
s的组合,运营商,正确使用observeOn
/ subscribeOn
,使用onError
进行错误处理,处理/取消订阅等等),因为您需要使用async api,您可以使用fromEmitter()
/ create()
(在较新的RxJava1版本中),阅读更多here:
private final Scheduler singleThreadScheduler = Schedulers.from(Executors.newSingleThreadExecutor());
public Observable<Result> execute() { // This method called many times from another classes
return Observable.fromEmitter(new Action1<Emitter<? extends Object>>() {
@Override
public void call(Emitter<?> emitter) {
emitter.setCancellation(() -> {
//cancel request on unsubscribing
});
makeRequest(result -> {
emitter.onNext(result);
});
}
})
.subscribeOn(singleThreadScheduler)
}