如何减少 Javascript 中多个变量的对象数组?
How to reduce an array of objects on multiple variables in Javascript?
我想知道如何根据多个属性减少大量对象。该数组看起来像:
[{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:6, district:12, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:14, district:19, to_timestamp:"2015-10-01T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"VANDALISM"},
...
{count:4, district:19, to_timestamp:"2016-03-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:7, district:10, to_timestamp:"2016-03-24T00:00:00.000Z", type:"ASSAULT"}]
生成的减少的对象数组需要包含在任何给定日期 (to_timestamp
) 的每个 district
给定犯罪 type
的聚合 count
;日期是每周一次。类似于:
[{key: "MOTOR VEHICLE THEFT", value: 57, date:"2015/09/23"},
...
{key: "ASSAULT", value: 77, date:"2016/03/23"}]
我已经在使用 Moment 进行日期转换。
您可以使用一个对象作为所需组(type
和 to_timestamp
)的散列 table,并使用 Array#forEach
迭代数组。
var data = [{ count: 4, district: 19, to_timestamp: "2015-09-24T00:00:00.000Z", type: "MOTOR VEHICLE THEFT" }, { count: 6, district: 12, to_timestamp: "2015-09-24T00:00:00.000Z", type: "MOTOR VEHICLE THEFT" }, { count: 14, district: 19, to_timestamp: "2015-10-01T00:00:00.000Z", type: "MOTOR VEHICLE THEFT" }, { count: 4, district: 19, to_timestamp: "2015-09-24T00:00:00.000Z", type: "VANDALISM" }, { count: 4, district: 19, to_timestamp: "2016-03-24T00:00:00.000Z", type: "MOTOR VEHICLE THEFT" }, { count: 7, district: 10, to_timestamp: "2016-03-24T00:00:00.000Z", type: "ASSAULT" }],
groupBy = ['type', 'to_timestamp'],
grouped = [];
data.forEach(function (a) {
var key = groupBy.map(function (k) { return a[k]; }).join('|');
if (!this[key]) {
this[key] = { key: a.type, value: 0, date: a.to_timestamp.slice(0, 10).replace(/-/g, '/') };
grouped.push(this[key]);
}
this[key].value += a.count;
}, Object.create(null));
console.log(grouped);
我想你可以用一个简单的 Array.prototype.forEach
循环来做到这一点:
var crimes = [
{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:6, district:12, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:14, district:19, to_timestamp:"2015-10-01T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"VANDALISM"},
{count:4, district:19, to_timestamp:"2016-03-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:7, district:10, to_timestamp:"2016-03-24T00:00:00.000Z", type:"ASSAULT"}
];
var dict = {},
result = [];
crimes.forEach(crime => {
var date = new Date(crime.to_timestamp);
date.setDate(date.getDate() - date.getDay());
var hash = crime.type + date.toDateString()
if (!dict[hash]) {
dict[hash] = {
count: crime.count,
key: crime.type,
date: date
};
result.push(dict[hash])
} else
dict[hash].count += crime.count;
});
console.log(result);
但我认为你减少一个对象比一个数组更容易。得到对象后,可以将其转换为数组
此代码只是将 data
和 type
组合到对象键。没有加district
.
const object = [{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:6, district:12, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:14, district:19, to_timestamp:"2015-10-01T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"VANDALISM"},
{count:4, district:19, to_timestamp:"2016-03-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:7, district:10, to_timestamp:"2016-03-24T00:00:00.000Z", type:"ASSAULT"}]
// reduce a object
.reduce( ( res, item) => {
const date = moment(item.to_timestamp).format('YYYY/MM/DD')
const key = item.type + date
if ( !res[key] ) {
res[key] = {key: item.type, date: date, value: item.count}
} else {
res[key]['value'] += item.count
}
return res
}, {} )
//get a object, and then the object to array
//console.log(object)
var result = []
for ( var key in object ) {
result.push(object[key])
}
console.log(result)
<script src="http://momentjs.com/downloads/moment.min.js"></script>
我想知道如何根据多个属性减少大量对象。该数组看起来像:
[{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:6, district:12, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:14, district:19, to_timestamp:"2015-10-01T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"VANDALISM"},
...
{count:4, district:19, to_timestamp:"2016-03-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:7, district:10, to_timestamp:"2016-03-24T00:00:00.000Z", type:"ASSAULT"}]
生成的减少的对象数组需要包含在任何给定日期 (to_timestamp
) 的每个 district
给定犯罪 type
的聚合 count
;日期是每周一次。类似于:
[{key: "MOTOR VEHICLE THEFT", value: 57, date:"2015/09/23"},
...
{key: "ASSAULT", value: 77, date:"2016/03/23"}]
我已经在使用 Moment 进行日期转换。
您可以使用一个对象作为所需组(type
和 to_timestamp
)的散列 table,并使用 Array#forEach
迭代数组。
var data = [{ count: 4, district: 19, to_timestamp: "2015-09-24T00:00:00.000Z", type: "MOTOR VEHICLE THEFT" }, { count: 6, district: 12, to_timestamp: "2015-09-24T00:00:00.000Z", type: "MOTOR VEHICLE THEFT" }, { count: 14, district: 19, to_timestamp: "2015-10-01T00:00:00.000Z", type: "MOTOR VEHICLE THEFT" }, { count: 4, district: 19, to_timestamp: "2015-09-24T00:00:00.000Z", type: "VANDALISM" }, { count: 4, district: 19, to_timestamp: "2016-03-24T00:00:00.000Z", type: "MOTOR VEHICLE THEFT" }, { count: 7, district: 10, to_timestamp: "2016-03-24T00:00:00.000Z", type: "ASSAULT" }],
groupBy = ['type', 'to_timestamp'],
grouped = [];
data.forEach(function (a) {
var key = groupBy.map(function (k) { return a[k]; }).join('|');
if (!this[key]) {
this[key] = { key: a.type, value: 0, date: a.to_timestamp.slice(0, 10).replace(/-/g, '/') };
grouped.push(this[key]);
}
this[key].value += a.count;
}, Object.create(null));
console.log(grouped);
我想你可以用一个简单的 Array.prototype.forEach
循环来做到这一点:
var crimes = [
{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:6, district:12, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:14, district:19, to_timestamp:"2015-10-01T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"VANDALISM"},
{count:4, district:19, to_timestamp:"2016-03-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:7, district:10, to_timestamp:"2016-03-24T00:00:00.000Z", type:"ASSAULT"}
];
var dict = {},
result = [];
crimes.forEach(crime => {
var date = new Date(crime.to_timestamp);
date.setDate(date.getDate() - date.getDay());
var hash = crime.type + date.toDateString()
if (!dict[hash]) {
dict[hash] = {
count: crime.count,
key: crime.type,
date: date
};
result.push(dict[hash])
} else
dict[hash].count += crime.count;
});
console.log(result);
但我认为你减少一个对象比一个数组更容易。得到对象后,可以将其转换为数组
此代码只是将 data
和 type
组合到对象键。没有加district
.
const object = [{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:6, district:12, to_timestamp:"2015-09-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:14, district:19, to_timestamp:"2015-10-01T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:4, district:19, to_timestamp:"2015-09-24T00:00:00.000Z", type:"VANDALISM"},
{count:4, district:19, to_timestamp:"2016-03-24T00:00:00.000Z", type:"MOTOR VEHICLE THEFT"},
{count:7, district:10, to_timestamp:"2016-03-24T00:00:00.000Z", type:"ASSAULT"}]
// reduce a object
.reduce( ( res, item) => {
const date = moment(item.to_timestamp).format('YYYY/MM/DD')
const key = item.type + date
if ( !res[key] ) {
res[key] = {key: item.type, date: date, value: item.count}
} else {
res[key]['value'] += item.count
}
return res
}, {} )
//get a object, and then the object to array
//console.log(object)
var result = []
for ( var key in object ) {
result.push(object[key])
}
console.log(result)
<script src="http://momentjs.com/downloads/moment.min.js"></script>