RxJs groupBy 多條件分組
前言
在Angular或Nest.Js中,使用groupBy分組資料相當方便
但應該是在Nest.Js使用到的機會最多XD
畢竟前端通常都是接到處理完的結果了,只需要渲染頁面就好
作法
比如下列資料,只需以shopId
分組
const array = [ {id: 1, shopId: 'a', category: 'AAA', name: 'Andy', birth: '1990/06/25'}, {id: 2, shopId: 'b', category: 'BBB', name: 'Ben', birth: '1989/01/01'}, {id: 3, shopId: 'a', category: 'AXX', name: 'Amy', birth: '1990/06/01'}, {id: 4, shopId: 'b', category: 'BXX', name: 'Brandon', birth: '1989/05/06'}, {id: 5, shopId: 'a', category: 'AAA', name: 'Anderson', birth: '1991/12/06'}, ]; from(array).pipe( groupBy(val => val.shopId), mergeMap(group => group.pipe(toArray()) ); // 得到結果如下: [ [ {id: 1, shopId: 'a', category: 'AAA', name: 'Andy', birth: '1990/06/25'}, {id: 3, shopId: 'a', category: 'AXX', name: 'Amy', birth: '1990/06/01'}, {id: 5, shopId: 'a', category: 'AAA', name: 'Anderson', birth: '1991/12/06'}, ], [ {id: 2, shopId: 'b', category: 'BBB', name: 'Ben', birth: '1989/01/01'}, {id: 4, shopId: 'b', category: 'BXX', name: 'Brandon', birth: '1989/05/06'} ] ]
但若想要多條件,依shopId + category當主鍵來分類
很遺憾不能在groupBy無腦的寫成groupBy(val => {shopId: val.shopId, category: val.category}),
後來在stack overflow(參考資料裡)查到解法
他的寫法摻了不少花括號,猛一看一瞬間還以為要寫的很複雜
但其實就是多一個mergeMap
,裡面再做一次groupBy
就好了!
以上述範例需求:依shopId + category當主鍵來分類
精簡後如下
from(array).pipe( groupBy(val => val.shopId), mergeMap(group => group.pipe(toArray()), mergeMap((_array) => from(_array).pipe( groupBy(val => val.category), // 第2個分組條件 mergeMap(group => group.pipe(toArray())), ) ), // 後面繼續串接所須的業務邏輯 ); // 得到結果如下: [ [ {id: 1, shopId: 'a', category: 'AAA', name: 'Andy', birth: '1990/06/25'}, {id: 5, shopId: 'a', category: 'AAA', name: 'Anderson', birth: '1991/12/06'}, ], [ {id: 3, shopId: 'a', category: 'AXX', name: 'Amy', birth: '1990/06/01'}, ], [ {id: 2, shopId: 'b', category: 'BBB', name: 'Ben', birth: '1989/01/01'}, {id: 4, shopId: 'b', category: 'BXX', name: 'Brandon', birth: '1989/05/06'} ] ]
若還有第三、第四個分組條件
依樣畫葫蘆繼續接mergeMap
參考資料
stack overflow / How to groupby by two fields from array using rxjs?