我是Rxjava的新手。 我有以下代码:
System.out.println("1: " + Thread.currentThread().getId());
Observable.create(new rx.Observable.OnSubscribe<String>() {
@Override
public void call(Subscriber<? super String> subcriber) {
System.out.println("2: " + Thread.currentThread().getId());
// query database
String result = ....
subcriber.onNext(result);
}
}).subscribeOn(Schedulers.newThread()).subscribe(countResult -> {
System.out.println("3: " + Thread.currentThread().getId());
});
例如,输出将为:
1:50
2:100
3:100
我希望订阅者在ID为50的线程上运行。我该怎么做?
答案 0 :(得分:1)
我认为有两种情况。您需要它在UI线程上运行,或者是因为同步。我知道你不能在特定的线程上调用一个函数,因为当调用该方法时它被绑定到线程的上下文,所以不可能从一个线程调用一个方法到另一个线程。您的问题是订阅方中的方法是从Schedulers.newThread()
调用的。我还发现了github issue关于Schedulers.currentThread()
的问题。您需要的是在调用观察者时通知调用者线程。
你也可以使用akka,用它来编写并发代码就更简单了。
抱歉我的语法不好。
答案 1 :(得分:0)
来自docs:
默认情况下,Observable和您应用的运算符链 它将完成其工作,并将在同一个线程上通知其观察员 调用其Subscribe方法。 SubscribeOn运算符 通过指定其中的不同调度程序来更改此行为 Observable应该运行。 ObserveOn运算符指定了一个 Observable将用于发送通知的不同Scheduler 对观察员来说。
因此,您可以使用subscribe代替 subscribeOn 在您创建的同一个帖子上观察您的收藏,如下所示:
Observable.create(new rx.Observable.OnSubscribe<String>() {
@Override
public void call(Subscriber<? super String> subcriber) {
System.out.println("2: " + Thread.currentThread().getId());
// query database
String result = ....
subcriber.onNext(result);
}
}).subscribe(countResult -> {
System.out.println("3: " + Thread.currentThread().getId());
});
<强>更新强> 如果您的应用程序是Android应用程序,您可以像在后台线程上一样使用subscribe,并使用Handler消息将结果传递给主线程。
如果您的应用程序是Java应用程序,我可能会建议使用wait()和notify()机制,或者考虑使用EventBus或akka等框架来处理更复杂的场景。
答案 2 :(得分:-1)
使用RxJava 1.0.15,您可以在toBlocking()
之前应用subscribe
,并且所有内容都将在创建整个运算符序列的线程上运行。
答案 3 :(得分:-1)
所以subscribeOn表示Observable将开始发出项目的线程,observeOn&#34; switch&#34;到可观察链的其余部分的线程。在订阅之前放置一个observeOn(schedulers.CurrentThread()),你将在创建此observable的线程中而不是在它执行的线程中。这里有一个解释rxjava线程的资源好。 http://www.grahamlea.com/2014/07/rxjava-threading-examples/
答案 4 :(得分:-1)
我相信@akarnokd是对的。您可以在没有.subscribeOn(Schedulers.newThread())
的情况下运行,以便它同步发生或在订阅之前使用toBlocking()
。或者,如果您只想在同一个线程上发生所有事情,但它不一定是当前线程,那么您可以这样做:
Observable
.defer(() -> Observable.create(...))
.subscribeOn(Schedulers.newThread())
.subscribe(subscriber);
defer
确保在订阅线程上发生对create
的调用。