Manipulate object property of an array [closed] - javascript

Closed. This question is not reproducible or was caused by typos. It is not currently accepting answers.
This question was caused by a typo or a problem that can no longer be reproduced. While similar questions may be on-topic here, this one was resolved in a way less likely to help future readers.
Closed 3 years ago.
Improve this question
I have an array of objects with some property. I wanted to do some math on the object property, and expect to return an array as well.
I've tried, doesn't seems to work.
array.map(el => {
el.count * 2;
return el
})
array = [{
count: 4,
string: 'randomstring'
}, {
count: 9,
string: 'randomstring'
}, {
count: 7,
string: 'randomstring'
}, {
count: 12,
string: 'randomstring'
}]
Expected
array = [{
count: 8,
string: 'randomstring'
}, {
count: 18,
string: 'randomstring'
}, {
count: 14,
string: 'randomstring'
}, {
count: 24,
string: 'randomstring'
}]

el.count * 2; will not change the value of el.count You could assign it to it like
el.count = el.count * 2;
But this will create another problem. It will change the original data. So better to return a new object with modified count property using Spread Operator
let array = [{ count: 4, string: 'randomstring' }, { count: 9, string: 'randomstring' }, { count: 7, string: 'randomstring' }, { count: 12, string: 'randomstring' }]
let res = array.map(el => ({...el,count:el.count*2}));
console.log(res);
You can also you Object.assign()
let res = array.map(el => Object.assign({count:el.count*2}));

You could map independent objects without mutating the original array.
newArray = array.map(o => Object.assign({}, o, { count: o.count * 2 }));
The same with spreading the object.
newArray = array.map(o => ({ ...o, count: o.count * 2 }));

Without explicitly mutating object's value (that's why we use map, filter and reduce in the first place):
array.map(({ count, string }) => (
{ count: count * 2, string }
));

try
array.map(e=>(e.count*=2,e))
let array = [
{ count: 4, string: 'randomstring' },
{ count: 9, string: 'randomstring' },
{ count: 7, string: 'randomstring' },
{ count: 12, string: 'randomstring' }
];
let r = array.map(e=>(e.count*=2,e))
console.log(r);

Related

Transform nested object of objects of arrays in JS

Besides the horrible name of the question my question is quite simple. I have this object:
let test = {
date1: [
{
time: 1,
value: 5,
},
{
time: 2,
value: 6,
},
],
date2: [
{
time: 1,
value: 20,
},
{
time: 2,
value: 10,
},
],
};
That I want to transform to something like this:
let result = {
date1: {
values: [5, 6],
times: [1, 2],
},
date2: {
values: [1, 2], // easier to summarise?!
times: [10, 20],
},
};
I actually want to do this in order to summarise the value-values for each date. I thought that if I have them in an array it would be easier to summarise them. I know there are other forms to do this (and I'd be happy to see any solutions).
My current approach does not what I want it to do. It looks like this:
let keys = Object.keys(test);
let red = keys.reduce((acc, curr) => {
return (acc[curr] = test[curr].map((e) => e.value));
}, {});
console.log(`red: `, red);
And produces this:
red: [ 20, 10 ]
This
return (acc[curr] = test[curr].map((e) => e.value));
is equivalent to
acc[curr] = test[curr].map((e) => e.value);
return acc[curr];
going inside a nested key of the accumulator on every iteration - which isn't the logic you want. Return the whole accumulator on a separate line, so previously assigned values don't get lost, and you also need to account for both the time and value properties of the array being iterated over - your => e.value only extracts one of the two properties you want.
let test = {
date1: [
{
time: 1,
value: 5,
},
{
time: 2,
value: 6,
},
],
date2: [
{
time: 1,
value: 20,
},
{
time: 2,
value: 10,
},
],
};
const keys = Object.keys(test);
const result = keys.reduce((acc, key) => {
acc[key] = {
values: test[key].map(({ value }) => value),
times: test[key].map(({ time }) => time),
};
return acc;
return acc;
}, {});
console.log(result);
or do
let test = {
date1: [
{
time: 1,
value: 5,
},
{
time: 2,
value: 6,
},
],
date2: [
{
time: 1,
value: 20,
},
{
time: 2,
value: 10,
},
],
};
const result = Object.fromEntries(
Object.entries(test).map(([key, arr]) => [
key,
{
values: arr.map(({ value }) => value),
times: arr.map(({ time }) => time),
}
])
);
console.log(result);
Try modifying it a little like this:
let result = Object.keys(test).reduce((acc, key) => {
test[key].forEach((item) => {
acc.push({
date: key,
time: item.time,
value: item.value,
});
});
return acc;
}
, []);
console.log(result);
Assuming all inner objects have the same keys and no date array is empty:
let test = {date1:[{time:1,value:5},{time:2,value:6},],date2:[{time:1,value:20},{time:2,value:10},]};
let keys = Object.keys(test);
let red = keys.reduce((acc, curr) => ({
...acc,
[curr]: Object.keys(test[curr][0])
.reduce((acc, key) => ({
...acc,
[key + 's']: test[curr].map(o => o[key])
}), {})
}), {});
console.log(`red: `, red);
There is no need to first create arrays when you want to sum up values from different objects. It looks like you want to achieve this result:
{
date1: 11
date2: 30
}
The idea to use reduce is fine (for summing up values). You can use Object.entries and Object.fromEntries on top of that, in order to create the new object structure:
const test = {date1: [{time: 1,value: 5,},{time: 2,value: 6,},],date2: [{time: 1,value: 20,},{time: 2,value: 10,},],};
const result = Object.fromEntries(
Object.entries(test).map(([key, arr]) =>
[key, arr.reduce((sum, {value}) => sum + value, 0)]
)
);
console.log(result);

Create object of objects from arrays [duplicate]

This question already has answers here:
How to combine two arrays into an array of objects? [duplicate]
(2 answers)
Closed 7 months ago.
I have two arrays in JavaScript:
a = [2, 5, 8, 10, 12, 15]
and
b = ["2022-01-01", "2022-01-02", "2022-01-03", "2022-01-04", "2022-01-05", "2022-01-06"]
I want to turn this into an object of objects, like so:
ts = {
{
value: 2,
time: "2022-01-01"
},
{
value: 5,
time: "2022-01-02"
},
{
value: 8,
time: "2022-01-03"
},
{
value: 10,
time: "2022-01-04"
},
{
value: 12,
time: "2022-01-05"
},
{
value: 15,
time: "2022-01-06"
}
}
I have looked at the forEach method and the reduce method, e.g. from https://bobbyhadz.com/blog/javascript-create-object-from-two-arrays , but I am struggling. Edit: my attempt was along the lines of:
const ts = {};
a.forEach((a_value, index) => {
ts.value[index] = a_value[index];
});
A simple for loop will work if both lists are the same size.
let a = [2, 5, 8, 10, 12, 15]
let b = ["2022-01-01", "2022-01-02", "2022-01-03", "2022-01-04", "2022-01-05", "2022-01-06"]
let ts = []
for (let idx in a) {
ts.push({value: a[idx],
time: b[idx]})
}
console.log(ts)

Sum object values with the same key

I am kinda new to javascript and today I encountered problem. Thing is, I have an array of amount of people visited every day by each hour (as you can see bellow). And I would like to find out most popular hour of day. My plan was to create a map where key is index of hour (0, 1, 2, 3, 4, 5...) and value is sum of all people who visited across all days on that hour. Problem is I'm not able to do that with my JS knowledge. Can someone give me a direction how to approach this problem? Thank you very much.
[
{date: "25.05.2018",
value: {
1: 209
2: 123
3: 890
.
.
24: 789
}
},
{date: "26.05.2018",
value: {
1: 280
2: 398
3: 450
.
.
24: 76
}
}
]
My JAVA like solution:
const { data: { data: [{ values }] } } = insightsData;
const timesMap = new Map();
values.forEach(item => {
Object.entries(item.value).forEach(([key, value]) => {
const timeValue = timesMap.get(key);
if (timeValue) {
timesMap.set(key, timeValue + value);
} else {
timesMap.set(key, value);
}
});
});
You could use Array#reduce with Array#map if you have arrays with the same length.
reduce takes an array as accumulator r and uses a logical OR || with a zero as value if an item does not exist in the accumulator.
var counts = [{ date: "26.05.2018", value: [125, 100, 200] }, { date: "27.05.2018", value: [5, 6, 7] }, { date: "28.05.2018", value: [3, 4, 5] }],
result = counts.reduce(
(r, { value }) => value.map((v, i) => (r[i] || 0) + v),
[]
);
console.log(result);
With objects as value properties.
var counts = [{ date: "26.05.2018", value: { 0: 125, 1: 100, 2: 200 } }, { date: "27.05.2018", value: { 0: 5, 1: 6, 2: 7 } }, { date: "28.05.2018", value: { 0: 3, 1: 4, 2: 5 } }],
result = counts.reduce(
(r, { value }) => Object
.entries(value)
.reduce((s, [k, v]) => {
s[k] = (s[k] || 0) + v;
return s;
}, r),
{}
);
console.log(result);
You can do iteratre over the values and add them to sum, like this
const data = {date: "26.05.2018",
value: [
125,
100,
200,
]
}
let sum = 0;
Object.values(data.value).forEach(elem => sum = sum + elem)
console.log(sum)
https://jsfiddle.net/5wwzn4yt/

Best way to returns keys from object in an array [duplicate]

This question already has answers here:
From an array of objects, extract value of a property as array
(24 answers)
Closed 4 years ago.
I have an array of objects like this:
var myArray = [{
key: 2,
value: 10,
},
{
key: 5,
value: 4,
},
{
key: 3,
value: 8,
},
{
key: 12,
value: 4,
}];
How is the most elegant way to convert this array in other just with the key numbers: [2,5,3,12]?
Use array.map
var myArray = [{
key: 2,
value: 10,
},
{
key: 5,
value: 4,
},
{
key: 3,
value: 8,
},
{
key: 12,
value: 4,
}];
console.log(myArray.map(a => a.key));
Use .map:
const myKeys = myArray.map(i => i.key);

Split object into two properties [duplicate]

This question already has answers here:
Convert object to array of key–value objects like `{ name: "Apple", value: "0.6" }`
(3 answers)
Closed 1 year ago.
a very beginner question below I'm sure, apologies for asking but I've had a good hunt on the matter with no luck... I'm looking to 'break' or 'expand' the following:
var words = { hello: 2, there: 3, heres: 1, text: 1 }
Into this:
var words = [{
word: 'hello',
count: 2
}, {
word: 'there',
count: 3
}, {
word: 'heres',
count: 1
}, {
word: 'text',
count: 1
}]
I've been messing around a lot with Underscore.js, but must be missing something very obvious. Any help will be greatly appreciated, thanks!
You can do this with Object.keys() and map().
var words = { hello: 2, there: 3, heres: 1, text: 1 }
var result = Object.keys(words).map(e => ({word: e, count: words[e]}))
console.log(result)
You can also first create array and then use for...in loop to push objects.
var words = { hello: 2, there: 3, heres: 1, text: 1 }, result = [];
for(var i in words) result.push({word: i, count: words[i]})
console.log(result)
Possible solution using Array#map.
const words = { hello: 2, there: 3, heres: 1, text: 1 },
res = Object.keys(words).map(v => ({ word: v, count: words[v] }));
console.log(res);
Or Array#reduce.
const words = { hello: 2, there: 3, heres: 1, text: 1 },
res = Object.keys(words).reduce((s,a) => (s.push({ word: a, count: words[a] }), s), []);
console.log(res);
Here's a solution using underscore's map function:
words = _.map(words, (v, k) => ({word: k, count: v}));
Underscore's map can iterate over an object. The first parameter to the iteratee is the value and the second parameter is the key.
let object = {
"06.10 15:00": 3.035,
"06.10 21:00": 3.001,
};
let arr = [];
for (const [key, value] of Object.entries(object)) {
arr.push({ date: key, value: value });
}
console.log(arr);

Categories

Resources