Reputation: 13
I'm a junior Web Developer, looking for some guidance solving a problem. Please excuse me if I'm missing anything integral, as this my first time posting here.
I have an array of some data returned like so:
[
{x: Date(1234), y: 0}
{x: Date(1235), y: 0}
{x: Date(1236), y: 300}
{x: Date(1237), y: 300}
{x: Date(1238), y: 300}
{x: Date(1239), y: 300}
{x: Date(1240), y: 300}
{x: Date(1241), y: 0}
{x: Date(1242), y: 0}
{x: Date(1243), y: 0}
]
If possible, I'd like to return a new array in which all consecutive 'y' values > 0 are summed. In the new array, the summed value should be associated with the first 'x' value of the summed items, like so:
[
{x: Date(1234), y: 0}
{x: Date(1235), y: 0}
{x: Date(1236), y: 1500}
{x: Date(1241), y: 0}
{x: Date(1242), y: 0}
{x: Date(1243), y: 0}
]
I'm thinking this will likely involve 'reduce,' but I'm a little unsure how to proceed. Any help would be greatly appreciated.
Thanks in advance!
Upvotes: 1
Views: 2284
Reputation: 4592
I think you can use a reduce function like this.
var arr = [{
x: Date(1234),
y: 0
},
{
x: Date(1235),
y: 0
},
{
x: Date(1236),
y: 300
},
{
x: Date(1237),
y: 300
},
{
x: Date(1238),
y: 300
},
{
x: Date(1239),
y: 300
},
{
x: Date(1240),
y: 300
},
{
x: Date(1241),
y: 0
},
{
x: Date(1242),
y: 0
},
{
x: Date(1243),
y: 0
}
];
var yGreaterThanZero = null;
var aggregated = arr.reduce(function(acc, cur) {
if (cur.y > 0) {
if (!yGreaterThanZero) {
acc.push(cur);
yGreaterThanZero = cur;
} else {
yGreaterThanZero.y += cur.y;
}
} else {
acc.push(cur);
}
return acc;
}, []);
console.log(aggregated);
Upvotes: 1
Reputation: 469
Using reduce, you could do something like this: https://jsbin.com/leladakiza/edit?js,console
var input = [
{x: Date(1234), y: 0},
{x: Date(1235), y: 0},
{x: Date(1236), y: 300},
{x: Date(1237), y: 300},
{x: Date(1238), y: 300},
{x: Date(1239), y: 300},
{x: Date(1240), y: 300},
{x: Date(1241), y: 0},
{x: Date(1242), y: 0},
{x: Date(1243), y: 0},
];
var output = input.reduce(function (acc, val) {
var lastIndex = acc.length - 1;
if (val.y <= 0 || lastIndex < 0 || acc[lastIndex].y <= 0) {
acc.push(val);
} else {
acc[lastIndex].y += val.y;
}
return acc;
}, []);
Upvotes: 2
Reputation: 4656
This is a very crude logic. We start recording when a value greater than 0 is obtained and push it at the end of the recording (value less than 0)
var a = [
{x: Date(1234), y: 0},
{x: Date(1235), y: 0},
{x: Date(1236), y: 300},
{x: Date(1237), y: 300},
{x: Date(1238), y: 300},
{x: Date(1239), y: 300},
{x: Date(1240), y: 300},
{x: Date(1241), y: 0},
{x: Date(1242), y: 0},
{x: Date(1243), y: 0},
{x: Date(1244), y: 200},
{x: Date(1245), y: 200},
{x: Date(1246), y: 200},
{x: Date(1247), y: 200},
]
var newA = [];
var recording = false;
var temp = {}
a.forEach(item => {
if (item.y > 0) {
recording = true;
if (temp.y) {
if(!temp.x) temp.x = item.x;
temp.y = temp.y + item.y
} else {
temp = item;
}
} else {
if (recording) newA.push(temp)
recording = false;
temp = {};
newA.push(item);
}
})
if (recording) newA.push(temp)
console.log(newA)
Upvotes: 0