Observables Push-Änderungen, und damit das Observable, nicht die Funktion, die darauf reagiert, hat die Kontrolle. Auf der anderen Seite müssen Generatoren Werte aus ihnen ziehen. Die Funktion, die auf den neuen Wert reagiert, legt fest, wann sie für einen neuen Wert bereit ist.
Ich hatte Probleme mit Gegendruck mit Observables, aber mit Generatoren können Sie Werte so langsam wie Sie wollen lassen.
Edit: die letzte Frage. Versprechen sind nur Observable, die nur einmal ausstrahlen, also glaube ich nicht, dass sie miteinander konkurrieren werden. Ich denke, der wahre Kampf wird async/erwarten vs Observables sein, und async/erwarten hat einen Vorsprung, und ist bereits in C# (und jetzt Node.js). Aber Observables haben dieses süße FRP-Feeling, und funktionales Programmieren ist super cool, also denke ich, dass sie beide mit einem guten Stück Verstand enden werden.
Edit2: André Staltz, Autor von Cycle.js und xstream, und Mitarbeiter Rx.js, schrieb ein großen Artikel auf, wie Generatoren und Observable beziehen (auf 2018.01.31). Insbesondere zeigt er, wie sie beide von einer gemeinsamen Basisklasse erben.
Und jetzt ein Verbraucher kann ein Listener ("Beobachter") oder ein Puller sein, es liegt an dem Verbraucher, ob es den Produzenten ziehen wird oder nicht.Und der Produzent kann ein Listenable ("beobachtbar") oder ein Pullable ("iterierbar") sein, es liegt beim Hersteller, ob er Daten proaktiv oder nur bei Bedarf sendet. Wie Sie sehen können, Verbraucher und Produzenten sind einfache Funktionen des gleichen Typs:
(num, Nutzlast) => void
So dass jeder Betreiber, die wir reaktive Programmierung oder iterable Programmierung bauen sowohl für die Arbeit, einfach weil die Grenze zwischen diesen beiden Modi unscharf wird und es nicht mehr um Observables im Vergleich zu Iterablen geht, geht es nur um Datentransformationen zwischen Produzenten und Konsumenten.
Ich empfehle es zu lesen [link]. Der Artikel stellt "Callbags" vor, eine Spezifikation für Rückrufe, die für reaktive und iterierbare Programmierung verwendet werden. Er implementiert diese Spezifikation, um a tiny library für iterable und reaktive Programmierung zu machen. Locken Sie den Artikel zu lesen und die Bibliothek zu überprüfen, sind hier einige Beispiele aus der 7kb lib basierend auf der Spezifikation stellt er:
Reactive Programmierbeispiel
Wählen Sie die ersten 5 ungerade Zahlen von einer Uhr dass jede Sekunde tickt, dann beginnen sie zu beobachten:
const {forEach, interval, map, filter, take, pipe} = require('callbag-basics');
pipe(
interval(1000),
map(x => x + 1),
filter(x => x % 2),
take(5),
forEach(x => console.log(x))
);
// 1
// 3
// 5
// 7
// 9
Iterable Programmierbeispiel
aus einem Bereich von Zahlen, von denen 5 aufzunehmen und sie durch 4 dividieren, dann anfangen, diese eine nach der anderen ziehen:
const {forEach, fromIter, take, map, pipe} = require('callbag-basics');
function* range(from, to) {
let i = from;
while (i <= to) {
yield i;
i++;
}
}
pipe(
fromIter(range(40, 99)), // 40, 41, 42, 43, 44, 45, 46, ...
take(5), // 40, 41, 42, 43, 44
map(x => x/4), // 10, 10.25, 10.5, 10.75, 11
forEach(x => console.log(x))
);
// 10
// 10.25
// 10.5
// 10.75
// 11
ein paar Anmerkungen: Async/Await auf Versprechungen baut, nicht Generatoren. Außerdem wurde der annullierbare Promise-Vorschlag kürzlich zurückgezogen. –
Wie Äpfel mit Orangen. Sie sind verschiedene Muster. Generatoren haben nichts mit Asynchronität zu tun. Wenn Sie sie benutzt haben, sollten Sie das wahrscheinlich wissen. Generatoren bieten ein Muster, das für einen asynchronen Kontrollfluss geeignet ist ("co" oder TS async/wartet auf die Implementierung für das ES6-Ziel), aber das ist alles. – estus
@estus, Ja. Generator ist keine wirklich asynchrone Lösung. Generator ist mehr wie eine Fabrik von Iteratoren. Wie Sie bereits erwähnt haben, löst es jedoch asynchrone Probleme durch Hinzufügen von "Q" - oder "Co" -Steuerflüssen. –