Обработка, такая как фильтрация, различение, преобразование массива объектов в последовательность объектов и обратно в массив объектов с использованием только RXJS - PullRequest
0 голосов
/ 27 декабря 2018

У меня есть альтернативное решение, но это больше похоже на использование большего количества функций не-rxjs при удалении дубликатов, фильтрации и преобразовании массива объектов.

, и это влияет на производительность, когда там 150–500 записей.

Вот проблески кодов

Модель машинописи

export class columns {
    public displayName: string;
    public fieldName: string;
    public tabName: string;
    public tabOrder: string;
}

, затем субъект поведения для передачи или перечисления массива столбцов из различных частей приложения.

public columnsNotify: BehaviorSubject<columns[]> = new BehaviorSubject([]);

Некоторые примеры данных

let listOfCols= [
    {displayName:"student name",fieldName:"stdName",tabName:"List",tabOrder:1},
    {displayName:"student id",fieldName:"stdid",tabName:"List",tabOrder:1},
    .....
    {displayName:"student name",fieldName:"stdName",tabName:"Details",tabOrder:2}
    {displayName:"student id",fieldName:"stdid",tabName:"Details",tabOrder:2}


];

this.columnsNotify.next(listOfCols);

Теперь текущее решение, которое я реализовал для , получает список вкладок с различными отчетами и сортирует их по порядку .

this.columnsNotify.pipe(
            map((column: columns[]) =>
                Array.from(
                    new Set(
                        column.map(mp => {
                            const obj = JSON.stringify({
                                tabName: mp.tabName,
                                tabOrder: mp.tabOrder
                            } as TabsInfo);

                            return obj;
                        })
                    )
                )
                    .map(data => JSON.parse(data))
                    .sort((a: TabsInfo, b: TabsInfo) => {
                        return a.tabOrder > b.tabOrder ? 1 : 0;
                    })
            )
        );

Я пытался улучшить приведенный выше код путем выравнивания массива, но остановился на операторе toArray, так как он ожидает ожидаемого завершения.

 this.columnsNotify.pipe(
        flatMap(searchCol => searchCol),
        map(
            (column: columns) =>
                new TabsInfo(column.tabName, column.tabOrder)
        ),
        distinct((tab: TabsInfo) => tab.tabName),
        take(3), //<-- Don't want this as, i don't know how many item there.
        toArray()  
    );

Итак, есть ли вообще использование оператора take с toArray?, или было бы хорошо совсем другой новый подход.

Мне нужно подобное решение в другом месте, где обработанные наблюдаемые будут использоваться в * ngFor, там также nпока удачи в использовании другой альтернативы.

Ответы [ 2 ]

0 голосов
/ 27 декабря 2018

toArray() - ваш разыскиваемый оператор, но проблема для вас заключается в следующем: flatMap(searchCol => searchCol),

Это ваше решение написать что-то вроде этого:

const expand = (items: columns[]) =>
  from(items).pipe(
    map((column: columns) => new TabsInfo(column.tabName, column.tabOrder)),
    distinct((tab: TabsInfo) => tab.tabName),
    toArray(),
  );

this.columnsNotify.pipe(
  switchMap((searchCol) => expand(searchCol)),
  tap((x) => console.log(x)),
);

Пожалуйста, используйте оператор switchMap(), который находится в более новом RxJS вместо flatMap().Кстати, mergeMap() - это новое имя для flatMap(), но в этом случае switchMap() лучше.

Если я правильно понял, проверил его на числах и работает так, как вы хотите.

0 голосов
/ 27 декабря 2018

Привет, не знаю, почему вы не можете просто сделать это так:

const obs$ = of(listOfCols);

obs$.pipe(
  flatMap(t => t),
  map(t => {return new TabsInfo(t.tabName, t.tabOrder)}),
  distinct((tab: TabsInfo) => tab.tabName),
  toArray(),
  map( array => array.sort())
  ).subscribe( // of course if you want to us it in *ngFor remove subscribe.
    t => console.log(t)
  )

Я думаю, что что-то упустил.

...