问题描述
说我有一本带有嵌套子词典的字典:
let dict =
{
"SEATTLE" : {
"gross_sales" : 106766,"price" : 584.50,"dates" : [ {
"date" : "2020-03-13","total_sales_to_date" : 2,"new_sales" : 2,},{
"date" : "2020-03-19","total_sales_to_date" : 5,"new_sales" : 3,}
]
},"PHOENIX" : {
"gross_sales" : 26691.5,"price" : 292.25,"total_sales_to_date" : 9,"new_sales" : 9,"total_sales_to_date" : 19,"new_sales" : 10,}
]
}
}
我想针对其他键/值对键/值对中的每个数值进行归一化,然后将其附加为 new 键/值对。
对于dates
时间序列数据数组,我想针对两个日期(数组内)和同一日期的其他位置(其他对象)对每个日期中的每个键/值对进行归一化)。
例如,这是手术后我要寻找的东西:
{
"SEATTLE" : {
"gross_sales" : 106766,"normalised_gross_sales" : 1.0,"normalised_price" : 1.0,"norm_total_sales_over_time" : 0.4,"norm_total_sales_over_locations" : 0.22222222,"norm_total_sales_over_time" : 1.0,"norm_total_sales_over_locations" : 0.26315789,"normalised_gross_sales" : 0.25,"normalised_price" : 0.5,"norm_total_sales_over_time" : 0.47368421,"norm_total_sales_over_locations" : 1.0,}
]
}
}
即:数组中最后一个日期的total_sales_to_date
值应标准化为1.0
的{{1}}
,并且数组中当前日期的所有对象(norm_total_sales_over_time
,total_sales_to_date
)的最大SEATTLE
值应归一化为PHOENIX
我发现这在JS中处理起来非常复杂。我的实际任务是将字典与数百个子字典进行比较,我正在寻找一种可扩展的解决方案。在norm_total_sales_over_locations
pandas
中,这是微不足道的,但是,我想学习如何使用现代javascript处理此问题,因为我正在使用{{1 }}解释器。
什么是有效的dataframe
JavaScript解决方案?
解决方法
以下是一种以上述方式返回标准化值的解决方案:
let dict = {
"SEATTLE": {
"gross_sales": 106766,"price": 584.50,"dates": [{
"date": "2020-03-13","total_sales_to_date": 2,"new_sales": 2,},{
"date": "2020-03-19","total_sales_to_date": 5,"new_sales": 3,}]
},"PHOENIX": {
"gross_sales": 26691.5,"price": 292.25,"total_sales_to_date": 9,"new_sales": 9,"total_sales_to_date": 19,"new_sales": 10,}]
}
}
async function normaliseDict(_dict) {
let values = await Object.values(_dict);
// make arrays with values from each key
let all_gross_sales = [];
let all_price = [];
let all_total_sales = {};
values.forEach((element) => {
all_gross_sales.push(element.gross_sales);
all_price.push(element.price);
let most_recent_total_sales_value = element.dates[element.dates.length - 1].total_sales_to_date;
element.dates.forEach((date,idx) => {
date.norm_total_sales_over_time = date.total_sales_to_date / most_recent_total_sales_value;
if (all_total_sales[date.date]) all_total_sales[date.date].push(date.total_sales_to_date);
else {
all_total_sales[date.date] = [];
all_total_sales[date.date].push(date.total_sales_to_date);
}
});
});
const newDict = values.map(ob => {
ob.gross_sales_norm = ob.gross_sales / Math.max(...all_gross_sales);
ob.price_norm = ob.price / Math.max(...all_price);
return ob;
});
values.forEach((element) => {
element.dates.forEach((date,idx) => {
date.norm_total_sales_over_locations_for_this_date = date.total_sales_to_date / Math.max(...all_total_sales[date.date]);
});
});
return await dict;
}
(async () => {
console.log(await normaliseDict(dict))
})()