0
:
{a: "5", b: "gg", X: "dd", Y: "dd", Z: "dd"}
1
:
{X: "dd", Y: "dd", Z: "dd"}
2
:
{X: "df", Y: "dd", Z: "dd"}
I want to compare these objects with each other so that i can not add repeated object in an array.
If I understand your question with given information, there can be 2 possible scenarios.
if you want to add one object to another object (merge) based on key than it can be done with angular.extend and the same key will be overwritten by later object keys
let inp1 = {a: "aa", b: "bb", X: "xx", Y: "yy", Z: "zz"};
let inp2 = {X: "xxx", Y: "yyy", Z: "zzz", W: "www"};
let inp3 = {X: "x3", Y: "y3", Z: "z3"};
angular.extend(inp1, inp2);
console.log("inp1", inp1);
// print {"a": "aa", "b": "bb", "X": "xxx","Y": "yyy","Z": "zzz","W": "www"}
if you simply want to compare two objects before adding into another object or (push into array) then you can do it with angular.equals
anguar.equals(inp2,inp3) // return false
Related
I've an object like this:
const obj = {a: {x: 0, y: 0}}
that could be also:
const obj = {a: {x: 0, y: 0}, b: {x: 10, y: 3}, abcd: {x: -1, y: 0}}
So, the obj can have more than one key and with variables key names.
I need to replace each x value with a a string like this ${x}% so the x value + the percentage symbol.
How can I do that?
The expected results should be:
const obj = {a: {x: 0, y: 0}} // {a: {x: '0%', y: 0}}
const obj = {a: {x: 0, y: 0}, b: {x: 10, y: 3}, abcd: {x: -1, y: 0}} // {a: {x: '0%', y: 0}, b: {x: '10%', y: 3}, abcd: {x: '-1%', y: 0}}
I tried looping the object but I don't know if there is a smartest solution
const obj = {a: {x: 0, y: 0}, b: {x: 10, y: 3}, abcd: {x: -1, y: 0}}
let result = Object.fromEntries(Object.entries(obj).map(([k,v]) => {
return [k,{...v,x:`${v.x}%`}]
}))
console.log(result)
You can also check the object recursively. So no matter how deep the object goes every given key that matches gets a suffix.
I also make sure to create a copy of the object to prevent altering the original object(s).
const obj = {a: {x: 0, y: 0}, b: {x: 10, y: 3}, abcd: {x: -1, y: 0}};
const addSuffixToObj = (obj, key, suffix) => {
const copy = {...obj};
Object.keys(copy).forEach((prop) => {
if (typeof copy[prop] === 'object') {
copy[prop] = addSuffixToObj(copy[prop], key, suffix);
}else if(prop === key){
copy[prop] = copy[prop] + suffix;
}
});
return copy;
}
// Add "%" to all "x" keys
const result = addSuffixToObj(obj, 'x', '%');
console.log(result);
You can get the array of object keys and then use forEach, it's a method that executes provided function for every element of array(here - for every object key):
Object.keys(obj).forEach(el => obj[el].x = `${obj[el].x}%`)
I have the following array:
0: {x: "/", y: 8}
1: {x: "/a", y: 7}
2: {x: "/a", y: 2}
3: {x: "/", y: 1}
How can I turn that into:
0: {x: "/", y: 9}
1: {x: "/a", y: 9}
Where the same values of X have their Y value added on.
It should only look for the same values of X, if they are the same it combines them and adds their Y together.
You can use Array#reduce with an object to store the values for each x.
let arr = [{x: "/", y: 8},{x: "/a", y: 7},{x: "/a", y: 2},{x: "/", y: 1}];
let res = Object.values(arr.reduce((acc,{x,y})=>{
(acc[x] = acc[x] || {x, y:0}).y += y;
return acc;
}, {}));
console.log(res);
I have an array of objects:
objArray = [
{x: 1, y: 7},
{x: 2, y: 14},
{x: 1, z: 9},
{x: 2, z: 18}
{x: 1, n: 6}
{x: 2, n: 16}
]
Is there an efficient way to merge for "X" without a for loop? so that I end up with:
objArray = [
{x: 1, y: 7, z: 9, n: 6},
{x: 2, y: 14, z: 18, n: 16}
]
So look for common objArray[n]["x"] and merge all hits into one object? It's OK to modify the original array or create a new one.
I'm aware this can be done with a loop, but I'm trying to avoid too many loops for this implementation, though I'm not sure if a reduce or a filter would work for this.
You could take a Map and group by property x.
var array = [{ x: 1, y: 7 }, { x: 2, y: 14 }, { x: 1, z: 9 }, { x: 2, z: 18 }, { x: 1, n: 6 }, { x: 2, n: 16 }],
result = Array.from(
array
.reduce((m, o) => m.set(o.x, Object.assign({}, m.get(o.x), o)), new Map)
.values()
);
console.log(result);
.as-console-wrapper { max-height: 100% !important; top: 0; }
You could use reduce method to build an object and then Object.values to get an array.
const data = [{"x":1,"y":7},{"x":2,"y":14},{"x":1,"z":9},{"x":2,"z":18},{"x":1,"n":6},{"x":2,"n":16}]
const res = data.reduce((r, {x, ...rest}) => {
if(!r[x]) r[x] = {x, ...rest}
else Object.assign(r[x], rest);
return r;
}, {})
const result = Object.values(res);
console.log(result)
You can do it with Array#reduce:
const objArray = [
{x: 1, y: 7},
{x: 2, y: 14},
{x: 1, z: 9},
{x: 2, z: 18},
{x: 1, n: 6},
{x: 2, n: 16},
]
const result = Object.values( objArray.reduce(
(p,c) => (p[c.x] = Object.assign( {}, p[c.x], c ), p ), {}
) );
console.log( result );
Why doesn't this test pass?
it('lodash_test', function() {
var arr = [{a: "x", b: [{x: "1", y: "2"}]}, {a: "x", b: [{x: "1", y: "2"}]}, {a: "x", b: [{x: "33", y: "2"}]}]
var result = _.filter(arr, function(obj) {
obj.b.forEach(function(item_b) {
if(item_b.x=="1") {
return true;
}
});
});
expect(result).to.be.eql([{a: "x", b: [{x: "1", y: "2"}]}, {a: "x", b: [{x: "1", y: "2"}]}]);
});
Because forEach's return value is completely ignored, and your _.filter predicate function never returns anything.
You probably wanted to use some:
it('lodash_test', function() {
var arr = [{a: "x", b: [{x: "1", y: "2"}]}, {a: "x", b: [{x: "1", y: "2"}]}, {a: "x", b: [{x: "33", y: "2"}]}]
var result = _.filter(arr, function(obj) {
return obj.b.some(function(item_b) {
// ^^^^^^^ ^^^^
if(item_b.x=="1") {
return true;
}
});
});
expect(result).to.be.eql([{a: "x", b: [{x: "1", y: "2"}]}, {a: "x", b: [{x: "1", y: "2"}]}]);
});
Array#some calls the predicate for each entry in the array, stopping the first time the predicate returns a truthy value; its return value is true if the predicate ever returned a truthy value, or false if not.
So the return I've underscored in the above is the return from the _.filter predicate; your original return true is the return from some (formerly forEach).
I have a problem with the logic to update the values in a json.
Initial json is
var val = {
"data": [
{x: 1396328400000, y: 92, num: "243"},
{x: 1425189600000, y: 91, num: "158"}
]
};
I want to duplicate data into another object data1 containing this in val.
Considering current month is March 2015, timeInMilliSeconds will give the value as 1425189600000, If the code encounters this value, it should replace the num in first data array to 0. Except the 1425189600000 in data1 all the values should be 0
Here is the jsfiddle
var date = new Date();
timeInMilliSeconds = Date.parse(date.getFullYear() + "/" +(date.getMonth()+1));
val = {
"data": [
{x: 1396328400000, y: 92, num: "243"},
{x: 1425189600000, y: 91, num: "0"}
],
"data1": [
{x: 1396328400000, y: 92, num: "0"},
{x: 1425189600000, y: 91, num: "158"}
]
};
Looks to me like you just need to update your check to make sure you're casting to a number:
if(k == 'num' && parseInt(val.data[prop]['x']) == timeInMilliSeconds) {