Я знаю о expand
для реализации рекурсии в rxjs.Я нашел много примеров того, как реализовать простую рекурсию, но ничего для взаимной рекурсии.
По сути, мне нужно поддерживать список результатов в актуальном состоянии.список фильтруется с помощью функции groom$
и обновляется / расширяется с помощью функции fetch$()
, каждая из которых вызывается поочередно.
Я выполнил первую реализацию с использованием конечного автомата (передавая следующую операцию для вызова expand
), но я хотел бы знать, есть ли лучший способ сделать взаимную рекурсию, используя rxjs.
Вот пример кода:
const { of, timer, throwError } = Rx;
const { expand, switchMap, map, concat } = RxOperators;
function groom$(arr) {
return timer(1000).pipe(map(() => arr.slice(1)));
}
function fetch$(arr) {
return timer(250).pipe(map(() => [...arr, arr.slice(-1)[0] + 1]));
}
function multiRecurse(initialState, firstOp, transitions) {
return firstOp(initialState).pipe(
map((data) => ({data, op: transitions[firstOp]})),
expand(({data, op}) => {
if (transitions[op]) {
return op(data).pipe(map((data) => ({data, op: transitions[op]})));
} else return throwError(`Unknown next operation: ${op}`);
}),
map(({data}) => data)
);
}
multiRecurse([0], fetch$, {
[groom$]: fetch$,
[fetch$]: groom$
});
Результирующая мраморная диаграмма (изhttps://rxviz.com/v/XJzlBj2o):