背景:项目中遇到table列表id相同的数据的单元格进行合并,想到通过id来分组实现
实现功能如下:
// 数组下标分组,可通过添加判断来达到不同的情况分组
const groupBy = (arr: any, f: any, key: string) => {
const groups = {}
arr.forEach((o: any, index: any) => {
const group = JSON.stringify(f(o))
groups[group] = groups[group] || []
if (o[key] != null) {
groups[group].push(index)
}
})
return Object.keys(groups).map((group: any) => {
return groups[group]
})
}
// 调用方式
const list = groupBy(tableData.value, (item: any) => {
return [item.DeliveryPalletId]
},'DeliveryPalletId')
根据单个属性来合并单元格没有问题,然后需求变动,需要根据多个属性来进行分组合并单元格,首先想到通过两个属性来进行相加,如果值相等来进行合并分组判断:
// 调用方式
const list = groupBy(tableData.value,(item: any) => {
const value = item.DeliveryPalletId+item.PalletStoredId
return [value]},'DeliveryPalletId')
按这个写法突然感觉不大对,如果我有很多个属性合并的时候,怎么能够达到分组效果呢,经过不断尝试,得出下面得写法:
// 数组多属性分组
const groupArray = (data: any, keys: any) => {
const list:any = []
const listObj = {}
data.forEach((item:any,index:number)=>{
let itemStr = ''
const itemArr:any = []
const itemObj = {}
keys.forEach((key:string,ind:number)=>{
itemArr.push(item[key])
itemObj[key] = item[key]
})
itemStr = itemArr.join('_')
if(!listObj[itemStr]){
list.push({
...itemObj,
indexChildren:[index],
children:[item]
})
listObj[itemStr] = item
}else{
list.forEach((listItem:any,ind:number)=>{
const isTrue = keys.some((key:any) => {
return listItem[key] !== item[key];
});
if (!isTrue) {
listItem.indexChildren.push(index)
listItem.children.push(item);
}
})
}
})
return list;
}
// 调用方式
const list = groupArray(tableData.value,['PalletStoredId','DeliveryPalletId'])
通过遍历数据数组和需要分组的key数组来进行判断得出,这个满足了我的需求,第二种方式应该也是可以实现的,但是要注意显示的时候数据排序的问题