У меня есть список объектов, который выглядит так, и я хочу превратить его в список значений по идентификатору.
Original = [
{id: 1, value: 12.2494, time: "00:00:00.14"},
{id: 1, value: 4.5141, time: "00:00:01.138"},
{id: 1, value: 2.85930, time: "00:00:02.138"},
{id: 1, value: 1.0364, time: "00:00:03.146"},
{id: 2, value: 4.3510, time: "00:09:15.157"},
{id: 2, value: 3.90, time: "00:09:16.115"},
{id: 2, value: 3.544, time: "00:09:17.116"},
{id: 2, value: 3.247, time: "00:09:18.157"}
]
Ожидаемый результат
data[1]={value:[12.494, 4.5141...],time: ["00:00:00.14","00:00:01.138"]...}
data[2]={value:[4.3510, 3.90...],time: ["00:09:15.157","00:09:16.115"]...}
Я пробовал что-то подобное, но возвращает только одно значение
var data= {};
original.forEach(function(item) {
var id = item.id;
data[id] = {
value:[],
time:[]
}
data[id].value.push(item['value']);
data[id].time.push(item['time']);
})
2 ответа
Вы можете использовать функцию reduce
из массивов.
Проверить текущий id
в аккумуляторе;
Если он существует, нажмите на уже сохраненные values
и times
Или создайте template object
и нажмите values
и times
var Original=[{id: 1, value: 12.2494, time: "00:00:00.14"},{id: 1, value: 4.5141, time: "00:00:01.138"},{id: 1, value: 2.85930, time: "00:00:02.138"},{id: 1, value: 1.0364, time: "00:00:03.146"},{id: 2, value: 4.3510, time: "00:09:15.157"},{id: 2, value: 3.90, time: "00:09:16.115"},{id: 2, value: 3.544, time: "00:09:17.116"},{id: 2, value: 3.247, time: "00:09:18.157"}];
var data = Original.reduce((a, c) => {
var current = (a[c.id] || (a[c.id] = {value: [], time: []}));
current.value.push(c.value);
current.time.push(c.time);
return a;
}, {});
console.log(data);
.as-console-wrapper { max-height: 100% !important; top: 0; }
Оригинальный ответ отлично работает, но если у вас есть иррациональное отвращение к использованию push (если объект создается и изменяется только при закрытии, действительно ли он меняется?):
const original = [
{id: 1, value: 12.2494, time: "00:00:00.14"},
{id: 1, value: 4.5141, time: "00:00:01.138"},
{id: 1, value: 2.85930, time: "00:00:02.138"},
{id: 1, value: 1.0364, time: "00:00:03.146"},
{id: 2, value: 4.3510, time: "00:09:15.157"},
{id: 2, value: 3.90, time: "00:09:16.115"},
{id: 2, value: 3.544, time: "00:09:17.116"},
{id: 2, value: 3.247, time: "00:09:18.157"}
]
const data = original.reduce((x, y) => x[y.id]
? Object.assign({}, x, {
[y.id]: {
value: x[y.id]
.value
.concat(y.value),
time: x[y.id]
.time
.concat(y.time)
}
})
: Object.assign({}, x, {
[y.id]: {
value: [y.value],
time: [y.time]
}
}), {})
Или, если в данных есть дыры, и вы не хотите добавлять undefined, уменьшите до уникальных идентификаторов, сопоставьте этот список, отфильтруйте исходный список, уменьшите до слияния:
const unoriginal = [
{id: 1, value: 12.2494, time: "00:00:00.14"},
{id: 1, value: 4.5141, time: "00:00:01.138"},
{id: 1, value: 2.85930, time: "00:00:02.138"},
{id: 1, value: 1.0364},
{id: 2, time: "00:09:15.157"},
{id: 2, value: 3.90, time: "00:09:16.115"},
{id: 2, value: 3.544, time: "00:09:17.116"},
{id: 2, value: 3.247, time: "00:09:18.157"}
]
const otherData = unoriginal.reduce((x, y) => x.includes(y.id)
? x
: x.concat(y.id), []).map(x => Object.assign({}, {
[x]: {
value: unoriginal
.filter(y => x === y.id)
.reduce((z, a) => a.value
? z.concat(a.value)
: z, []),
time: unoriginal
.filter(y => x === y.id)
.reduce((b, c) => c.time
? b.concat(c.time)
: b, [])
}
})).reduce((x, y) => Object.assign.apply(null, [x].concat(y)))
Похожие вопросы
Новые вопросы
javascript
По вопросам программирования на ECMAScript (JavaScript / JS) и его различных диалектах / реализациях (кроме ActionScript). Включите все соответствующие теги в свой вопрос; например, [node.js], [jquery], [json] и т. д.