[英]RxJava - When to use Observable with create method
我正在閱讀教程:
http://code.tutsplus.com/tutorials/getting-started-with-reactivex-on-android--cms-24387
特別是RxAndroid,但它和RxJava幾乎相同。 我不確定我完全理解這個概念。
下面我寫了一個方法,然后是一個示例用法。
我的問題是:這是實現我的函數的正確方法,以便我可以異步地在其他線程上運行它們嗎? 實際上,它們只會返回一個運行真實代碼的已創建的Observable,並處理錯誤和所有這些內容。
或者這是錯的,那么我想知道正確的方法。
Observable<String> googleSomething(String text){
return Observable.create(new Observable(){
@Override
public void call(Subscriber<? super String> subscriber) {
try {
String data = fetchData(text); // some normal method
subscriber.onNext(data); // Emit the contents of the URL
subscriber.onCompleted(); // Nothing more to emit
} catch(Exception e) {
subscriber.onError(e); // In case there are network errors
}
}
});
}
googleSomething("hello world").subscribeOn(Schedulers.io()).observeOn(Schedulers.immediate()).subscribe(...)
還使用Schedulers.immediate()來執行當前線程上的訂戶代碼? 它說“創建並返回一個在當前線程上立即執行工作的調度程序。” 在javadoc,但我不確定。
除非您更有經驗並需要自定義運算符或想要橋接基於舊版addListener / removeListener的API,否則不應該以create
開頭。 StackOverflow上有幾個問題使用了create
並且是麻煩的來源。
我更喜歡fromCallable
,它讓你生成一個單獨的值或拋出異常,因此不需要那些冗長的defer
+ just
來源。
Schedulers.immediate()
立即在調用者的線程上執行其任務,該線程是示例中的io()線程,而不是主線程。 目前,不支持將計算移回Java主線程,因為它需要阻止蹦床,並且通常是一個壞主意。
你幾乎不應該使用create()
,尤其不是初學者。 有更簡單的方法來創建observable,而create()
很難正確實現。
大多數情況下,您可以使用defer()
輕松繞過create()
defer()
。 例如,在這種情況下你會這樣做:
Observable<String> googleSomething(String text) {
return Observable.defer(new Func0<Observable<String>>() {
@Override
public Observable<String> call() {
try {
return Observable.just(fetchData(text));
} catch (IOException e) {
return Observable.error(e);
}
}
});
}
如果您沒有使用已檢查的異常,那么您甚至可以擺脫try-catch。 RxJava會自動將任何RuntimeException
轉發給訂閱者的onError()
部分。
您可以通過Observable.create(new OnSubscribe {})方法創建Observable:
Schedulers.immediate()將在它已經存在的線程上保持Observable處理 - 所以在你的情況下它將是Schedulers.io線程之一
你的代碼看起來不錯。 如果你不確定是否在另一個線程上運行。 你可以在調用.subscribe()
后立即打印一些內容,並查看輸出的順序。
googleSomething("hello world").subscribeOn(Schedulers.io()).observeOn(Schedulers.immediate()).subscribe(...)
System.out.println("This should be printed first");
嘗試在fetchData()
模擬長時間運行的操作, fetchData()
立即打印其他內容。 因為.subscribe()是非阻塞的“這應該先打印”實際上是先打印。
或者,您可以使用打印當前線程。
Thread.currentThread().getName()
在您的observable內外使用它,輸出應該不同。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.