La convención de nombres *Async

Cada operador perezoso y de agregación tiene un gemelo que trabaja sobre FxAsyncIterable: mismo comportamiento, con un callback apto para async.

Iterable<B> map<A, B>(B Function(A a) f, Iterable<A> iterable) FxAsyncIterable<B> mapAsync<A, B>(FutureOr<B> Function(A a) f, FxAsyncIterable<A> iterable) Future<List<A>> toListAsync<A>(FxAsyncIterable<A> iterable) Future<A> reduceAsync<A>(FutureOr<A> Function(A acc, A a) f, FxAsyncIterable<A> iterable) Fx<R> Fx.map<R>(R Function(T a) f) // sync chain FxAsync<R> FxAsync.map<R>(FutureOr<R> Function(T a) f) // async chain — same name!

Lección

Como Dart no tiene currificación sin tipos, FxDart no puede sobrecargar un único map para que funcione sobre Iterable y FxAsyncIterable en posición data-first: los tipos de los parámetros chocarían. Por eso cada operador perezoso y de agregación se publica en dos formas de nivel superior: la normal para Iterable, y un gemelo *Async para FxAsyncIterable cuyo callback devuelve FutureOr<R> en lugar de R. Ya has visto algunos: map/mapAsync, filter/filterAsync, toList/toListAsync, reduce/reduceAsync, fold/foldAsync, each/eachAsync, find/findAsync: el patrón se cumple prácticamente para todas las funciones de la librería.

Las formas encadenadas no necesitan esta división. En cuanto llamas a .toAsync() (o empiezas desde fxAsync/fxStream), cada método posterior de esa cadena FxAsync conserva su nombre normal.map(...), no .mapAsync(...) — porque el tipo del receptor ya le dice a Dart qué sobrecarga usar. El sufijo solo existe en el nivel superior, donde las llamadas data-first lo necesitan para desambiguar.

Demo 1 · Unos cuantos gemelos, uno al lado del otro

Las llamadas data-first siempre necesitan el sufijo Async en cuanto trabajas con un FxAsyncIterable:

Demo 2 · Forma data-first frente a forma encadenada

La forma encadenada se lee igual que su equivalente síncrona —sin sufijos— una vez que .toAsync() ha cambiado el tipo del receptor:

Pruébalo tú

Ejercicio: usa el gemelo data-first *Async de map para poner en mayúsculas cada nombre de este pipeline asíncrono.

Relacionado: toAsync — donde empiezan los pipelines asíncronos · Puentes con Stream — fromStream, fxStream, toStream · concurrent — evaluación en paralelo · map — el original síncrono