我的redux存储区中有两个对象。第一个按其ID持有支出。第二个以日期为键保存所有支出id。
ID支出
expenditures: {
byId: {
'0e1ca91f-aad2-44c7-985a-dfd014bb67fa': {
id: '0e1ca91f-aad2-44c7-985a-dfd014bb67fa',
createdAt: 1480510965381,
description: 'shoes',
categoryId: 13,
value: -4,
day: 1440374400000
},
'65711ad0-407d-42ca-aa13-c468a56d6ee6': {
id: '65711ad0-407d-42ca-aa13-c468a56d6ee6',
createdAt: 1480510965470,
description: 'groceries',
categoryId: 12,
value: -53.65,
day: 1440374400000
},
},
}
按天计算的支出
expenditures: {
byDays: {
'1440374400000': [
'0e1ca91f-aad2-44c7-985a-dfd014bb67fa',
'65711ad0-407d-42ca-aa13-c468a56d6ee6'
],
'1440720000000': [
'02180819-3684-480a-96c4-e9fceb2557d0',
'2201f929-7390-4b24-ba6b-b92e850fb964',
'f492ad3a-c580-429a-8b68-a2259658d0cd',
'f654725a-8eee-4e9a-97a8-4fd5a331473e',
'eedc5a7d-0320-41a1-b190-79f967b42961'
],
}
}
为了现在在我的组件中呈现这些内容,我需要一个基于按天支出的新对象
类似这样的东西:
expenditures: {
byDay: {
'1440374400000': [
{
id: '0e1ca91f-aad2-44c7-985a-dfd014bb67fa',
createdAt: 1480510965381,
description: 'shoes',
categoryId: 13,
value: -4,
day: 1440374400000
},
{
id: '65711ad0-407d-42ca-aa13-c468a56d6ee6',
createdAt: 1480510965470,
updatedAt: 1480510965470,
description: 'groceries',
categoryId: 12,
value: -53.65,
day: 1440374400000
}
],
}
}
到目前为止我所拥有的:
Object.keys(state.expenditures.byDays)
.filter((day) => day >= currentFirstDay && day <= currentLastDay)
.sort((a, b) => b - a)
这给了我一个基于expenses.byDays的过滤和排序数组。但是,我不知道如何进行。在过去的几个小时里,我使用reduce
尝试了一些方法,但无法修复。
感谢帮助!
答案 0 :(得分:1)
我能想到的解决方案。请参阅下面的repl
const state = {
expenditures: {
byId: {
'0e1ca91f-aad2-44c7-985a-dfd014bb67fa': {
id: '0e1ca91f-aad2-44c7-985a-dfd014bb67fa',
createdAt: 1480510965381,
description: 'shoes',
categoryId: 13,
value: -4,
day: 1440374400000
},
'65711ad0-407d-42ca-aa13-c468a56d6ee6': {
id: '65711ad0-407d-42ca-aa13-c468a56d6ee6',
createdAt: 1480510965470,
description: 'groceries',
categoryId: 12,
value: -53.65,
day: 1440374400000
},
},
byDays: {
'1440374400000': [
'0e1ca91f-aad2-44c7-985a-dfd014bb67fa',
'65711ad0-407d-42ca-aa13-c468a56d6ee6'
],
'1440720000000': [
'02180819-3684-480a-96c4-e9fceb2557d0',
'2201f929-7390-4b24-ba6b-b92e850fb964',
'f492ad3a-c580-429a-8b68-a2259658d0cd',
'f654725a-8eee-4e9a-97a8-4fd5a331473e',
'eedc5a7d-0320-41a1-b190-79f967b42961'
],
}
}
}
//Pull out relevant piece of state from redux
const byDays = state.expenditures.byDays;
const byId = state.expenditures.byId;
// convert Id to Object
const idToObjectReducer = (acc,key) => {
if(byId[key]) {
acc.push(byId[key]);
}
return acc;
};
// Sort Objects by date
const sortByDateComparator = ({createdAt : date1}, {createdAt : date2}) => date1 - date2;
// convert byDays object
const rootReducer = (acc, key) => {
acc[key] = byDays[key].reduce(idToObjectReducer, []).sort(sortByDateComparator)
return acc;
};
const result = Object.keys(byDays).reduce(rootReducer, {});
console.log(result);
答案 1 :(得分:0)
您有正确的想法。但是,从byId
结构开始很有意义,因此您从一开始就使用所有信息。由于byId
对象中的支出已经具有day
信息,因此您可以忽略byDay
对象。
因此,从以下结构开始:
const expenditures = {
byId: {
'0e1ca91f-aad2-44c7-985a-dfd014bb67fa': {
id: '0e1ca91f-aad2-44c7-985a-dfd014bb67fa',
createdAt: 1480510965381,
description: 'shoes',
categoryId: 13,
value: -4,
day: 1440374400000
},
'65711ad0-407d-42ca-aa13-c468a56d6ee6': {
id: '65711ad0-407d-42ca-aa13-c468a56d6ee6',
createdAt: 1480510965470,
description: 'groceries',
categoryId: 12,
value: -53.65,
day: 1440374400000
},
}
}
我们假设第一天和最后一天的设置如下:
const currentFirstDay = 1440374400000;
const currentLastDay = 1440374400000;
然后,您可以对expenditures.byId
进行过滤和排序,然后生成一个新对象:
const filtered = Object.values(expenditures.byId)
.filter(expenditure => expenditure.day >= currentFirstDay && expenditure.day <= currentLastDay)
.sort((a, b) => b.value - a.value);
let byDay = {}
filtered.forEach(expenditure => {
if (!byDay[expenditure.day]) byDay[expenditure.day] = [];
byDay[expenditure.day].push(expenditure);
})
这将导致以下结果:
{
"1440374400000": [
{
categoryId: 13,
createdAt: 1480510965381,
day: 1440374400000
description: 'shoes',
id: '0e1ca91f-aad2-44c7-985a-dfd014bb67fa',
value: -4
},
{
categoryId: 12,
createdAt: 1480510965470,
day: 1440374400000
description: 'groceries',
id: '65711ad0-407d-42ca-aa13-c468a56d6ee6',
value: -53.65
}
]
}