RxJava Advent Calendar 2017 Gestern war @ toastkidjps "Laufzeitberechtigung mit RxPermissions verarbeiten". Der dritte Tag ist @ guignols "RxAndroid and RxSwing Scheduler". Eine interessante Geschichte über die Implementierung von Scheduler.
Am zweiten Tag lief niemand, also ist es schon eine Weile her, aber ich werde einen Artikel schreiben.
Zu wissen, wofür das nützlich ist, verbessert Ihre Motivation beim Lernen. Ich dachte, es könnte eine Möglichkeit geben, mit dem Lernen zu beginnen, nachdem ich wusste, welche Art von Bibliothek RxJava kann? ", Also machte ich RxJava zur" asynchronen Verarbeitung ". Stellen wir uns das als eine Java-Bibliothek vor, die das Schreiben erleichtert.
Personen, die an RxJava interessiert sind, es aber noch nicht verwendet haben (insbesondere Android-App-Entwickler)
Beschreibung von RxJava als Bibliothek, die das Schreiben von asynchroner Verarbeitung erleichtert
RxJava wird als Bibliothek bereitgestellt und kann mit Maven oder Gradle installiert werden.
Es muss die folgende Version oder höher sein.
Name | Version |
---|---|
Java | 1.6- |
Android | 2.3- |
RxJava wird häufig in der Entwicklung von Android-Apps verwendet, ist jedoch nicht auf Android beschränkt und kann in regulären Java- und Kotlin-Anwendungen verwendet werden.
Beachten Sie, dass RxJava2 eine eigene Definition der erforderlichen Funktionsschnittstelle hat, also Java 8 oder höher Funktionstyp-Schnittstelle des Pakets java.util.function (Funktion, Verbraucher Usw.) und sind nicht mit ihnen kompatibel.
Fügen Sie einfach eine Zeile zu build.gradle hinzu. Zum Zeitpunkt des Schreibens dieses Artikels war 2.1.7 das neueste.
app/build.gradle
dependencies {
implementation 'io.reactivex.rxjava2:rxjava:2.1.7'
Für die Entwicklung von Android-Apps ist es hilfreich, eine weitere Zeile hinzuzufügen, RxAndroid. Vielmehr macht es wenig Sinn, RxJava ohne es einzuschließen. Der Hauptzweck besteht darin, Scheduler zu verwenden (um den Ausführungsthread des Prozesses anzugeben), um den Prozess im Hauptthread von Android auszuführen. Die neueste Version ist 2.0.1.
app/build.gradle
implementation 'io.reactivex.rxjava2:rxandroid:2.0.1'
Wenn Sie Lambda-Ausdrücke verwenden möchten, müssen Sie Retrolambda oder Android Gradle Plugin 3.0 installieren, aber wir werden sie hier weglassen.
Sowohl RxJava als auch RxAndroid Es ist unter Apache License 2.0 lizenziert. Wenn Sie es verwenden möchten, müssen Sie die Lizenz in die App schreiben. Für Android-Apps kann com.google.gms: oss-licenses hilfreich sein.
Anzeigen von Open Source-Lizenzen mit com.google.gms: oss-licenses
Ich habe mich gefragt, ob es im RxJava-Einführungsartikel nicht viele Artikel gibt, die Single (einen Wert oder Abschluss oder Fehler benachrichtigen) und Completable (Abschluss oder Fehler benachrichtigen) verwenden. Daher werde ich ein Beispiel mit beiden vorstellen. Machen. Ich denke, dass die Desynchronisation der Verarbeitung auf feiner Ebene, die die Spezialität von RxJava ist, hauptsächlich durch die Verwendung von Single / Maybe / Completable realisiert werden kann, und ich verwende sie häufig in der tatsächlichen Entwicklung.
ExecutorService Dies kann bei der Verarbeitung mit dem herkömmlichen ExecutorService so geschrieben werden.
Machen Sie die Engpassmethode asynchron
final ExecutorService executor = Executors.newSingleThreadExecutor();
executor.execute(() -> bottleneckMethod());
executor.shutdown();
RxJava Dies ist in RxJava wie folgt geschrieben.
Machen Sie die Engpassmethode asynchron(RxJava)
Completable.fromAction(() -> bottleneckMethod())
.subscribeOn(Schedulers.newThread())
.subscribe();
subscribeOn ist eine Methode, die den Ausführungsthread für die gesamte Reihe von Prozessen angibt. Im obigen Code wird angegeben, dass ein neuer Thread erstellt und die Verarbeitung dort ausgeführt wird.
Die Funktion von RxJava ist, dass keine Verarbeitung ausgeführt wird, bis subscribe () aufgerufen wird. Zum Beispiel im Fall des folgenden Codes
Completable completable = Completable.fromAction(() -> bottleneckMethod())
.subscribeOn(Schedulers.newThread());
System.out.println("start");
completable.subscribe();
Das Ausführungsergebnis ist wie folgt.
Ausführungsergebnis
start
RxNewThreadScheduler-1 bottle neck
end.
Das Ergebnis der println-Methode, die vor subscribe () ausgeführt wurde, wird zuerst in die Standardausgabe ausgegeben.
ExecutorService Schreiben wir auf die gleiche Weise mit der traditionellen API.
Verwenden Sie das Ergebnis der asynchronen Verarbeitung(ExecutorService)
final ExecutorService executor = Executors.newSingleThreadExecutor();
final Future awaitable = executor.submit(() -> anyReturnBottleneckMethod());
executor.shutdown();
try {
System.out.println(awaitable.get(2, TimeUnit.SECONDS));
} catch (InterruptedException e) {
e.printStackTrace();
} catch (TimeoutException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
RxJava Der gleiche Prozess wird mit RxJava wie folgt geschrieben.
Verwenden Sie das Ergebnis der asynchronen Verarbeitung(RxJava)
Single.create(emitter -> emitter.onSuccess(anyReturnBottleneckMethod()))
.subscribeOn(Schedulers.newThread())
.subscribe(System.out::println, Throwable::printStackTrace);
Da wir das Verarbeitungsergebnis verwenden müssen, verwenden wir Single, um den Wert zu benachrichtigen. Es ist möglich, die Verarbeitung zu definieren, wenn im zweiten Argument der Subscribe-Methode ein Fehler auftritt.
Übrigens können Sie auch mit fromCallable schreiben, anstatt zu erstellen. Aufrufbar ist java.util.concurrent.Callable. Entspricht Lieferant, der in Java 8 hinzugefügt wurde, und einem Funktionstyp, der den Wert verzögert. In der Benutzeroberfläche wurde es in Java 1.5 hinzugefügt, sodass es anscheinend umgeleitet wurde. Andererseits bin ich mir nicht sicher, da Runnable nicht verwendet wird und eine Funktionsschnittstelle namens Action separat definiert wird.
fromCallable
Single.fromCallable(() -> anyReturnBottleneckMethod())
RxJava kann Ihnen helfen, wenn Sie diese Art von Wartecode für die asynchrone Verarbeitung schreiben möchten.
Wichtig ist, dass Sie die richtigen Tools für das Problem verwenden, das Sie lösen möchten. ExecutorService ist eine gute API zum Schreiben von Code, der große Aufgaben parallel ausführt, und es ist möglich, dass Sie nicht auf eine solche Verarbeitung warten können, aber nicht gut darin sind.
Wenn Sie beispielsweise networkRequest () in einem E / A-Thread ausführen und das Ergebnis in TextView anzeigen möchten, können Sie wie folgt schreiben.
Aktualisieren Sie die Benutzeroberfläche mit den Ergebnissen der Netzwerkkommunikation
Single.create(emitter -> networkRequest())
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(textView::setText)
Beides sind Methoden zum Festlegen des Ausführungsthreads der Verarbeitung. watchOn ändert den Ausführungsthread von der folgenden Methode. Die Spezifikation in watchOn hat Vorrang vor der Spezifikation in subscribeOn.
Im vorherigen Code ändert sich der Ausführungsthread wie folgt.
Aktualisieren Sie die Benutzeroberfläche mit den Ergebnissen der Netzwerkkommunikation
Single.create(emitter -> networkRequest()) // I/O Faden
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(textView::setText) //Haupt-Bedroung
Sie könnten so denken.
Unter Android ist es wichtig, dass es Einschränkungen gibt, z. B. "Netzwerkkommunikation muss im Hintergrund-Thread sein" und "Update anzeigen muss im Haupt-Thread sein". Wenn Sie dagegen verstoßen, tritt eine Laufzeitausnahme auf und die App stürzt ab. Ich werde. Es gibt verschiedene Mechanismen wie Handler & Looper, um die Einschränkung zu vermeiden. Sie können dasselbe mit ihnen tun, aber mit RxJava (und RxAndroid) können Sie einfacheren Code schreiben.
Sie müssen nicht so viel lernen, weil Sie nur Stream API + α kennen müssen, um es zum Schreiben zu verwenden, aber es ist einfach eine ziemlich große Bibliothek, so dass es eine beträchtliche Zeit in Anspruch nehmen wird, sie vollständig zu verstehen. Obwohl es sich nicht um Android handelt, habe ich gehört, dass sich das Unternehmen für Letzteres entschieden hat, da die Lernkosten von Rx zu einem Engpass wurden, indem die Lernkosten von RxSwift + die Einführungskosten von MVVM und die Einführungskosten von Clean Architecture abgewogen wurden. Es scheint, dass die Implementierung von Rx-Serien in jeder Sprache ähnlich ist. Daher kann es für Entwickler, die in anderen Sprachen arbeiten, von Vorteil sein, reibungslos einzutreten. Im Gegenteil, es wird für Personen, die Rx noch nicht kennen, schwierig sein, daran teilzunehmen Sie müssen auch darüber nachdenken.
Wenn Sie RxJava2 ab Ende 2017 in Ihre Android-App integrieren, erhöht sich die Anzahl der Methoden um knapp 10.000. Es ist keine kleine Zahl, und je nach Projekt kann es das Limit überschreiten und Sie können gezwungen sein, es MultiDex zu machen. Tatsächlich ist dies bei den Apps der Fall, die ich bei der Arbeit entwickle. Einmal installiert, kann es schwierig sein, es zu entfernen (zu viel für die Bequemlichkeit), daher sollten Sie auch Alternativen in Betracht ziehen. Wenn Sie Kotlin verwenden, stellen Sie sicher, dass Sie Coroutine überprüfen (obwohl ich es überhaupt nicht überprüft habe).
Ich habe RxJava als "eine Bibliothek eingeführt, die das Schreiben von asynchroner Verarbeitung erleichtert". RxJava, mit dem Sie den Ausführungsthread in kleinen Einheiten angeben können, wird von Android-App-Entwicklern, die Einschränkungen für den Ausführungsthread im Framework haben, weitgehend akzeptiert.
Wichtig ist, dass Sie die richtigen Tools für das Problem verwenden, das Sie lösen möchten. ExecutorService ist ein Tool zum parallelen Ausführen großer Prozesse, und RxJava eignet sich relativ gut für die Desynchronisation in kleinen Einheiten, wie hier erläutert.
"RxJava Reactive Programming" (Shoyusha) ... Es ist eine Weile her, seit es veröffentlicht wurde, aber zu diesem Zeitpunkt Es ist das detaillierteste und leicht verständliche Buch in japanischer Sprache.
Recommended Posts