Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Merge two objects but only existing properties

Tags:

javascript

I have two objects. And I want to merge the two objects but only the property value who is only present to the first object.

   obj1 : {
        "name": "",
        "age": ""
   }

  obj2 : {
        "name": "Leo",
        "age": "14",
        "company": "aero",
        "shift": "night"
  }

The output I want to be is:

  obj1 : {
        "name": "Leo",
        "age": "14"
   }

The company and shift is no need to merge because that 2 property is not present in obj1.

The code I've done so far is: Object.assign({}, obj1, obj2);

But it's not give me the right output. What it gives is:

 merge : {
        "name": "Leo",
        "age": "14",
        "company": "aero",
        "shift": "night"
  }

Could someone help me how to achieve the output like this:

  merge : {
        "name": "Leo",
        "age": "14",
  }

Many thanks!

like image 495
Zero Avatar asked Nov 13 '16 11:11

Zero


3 Answers

Assuming you only want enumerable properties, this is easily done with Object.keys and in (or hasOwnProperty):

Object.keys(obj2).forEach(function(key) {
    if (key in obj1) { // or obj1.hasOwnProperty(key)
        obj1[key] = obj2[key];
    }
});

Example:

var obj1 = {
  "name": "",
  "age": ""
};

var obj2 = {
  "name": "Leo",
  "age": "14",
  "company": "aero",
  "shift": "night"
};

Object.keys(obj2).forEach(function(key) {
  if (key in obj1) { // or obj1.hasOwnProperty(key)
    obj1[key] = obj2[key];
  }
});
console.log(obj1);

Or in ES2015 syntax (since you mentioned Object.assign):

for (const key of Object.keys(obj2)) {
    if (key in obj1) { // or obj1.hasOwnProperty(key)
        obj1[key] = obj2[key];
    }
}

Or a more fluent approach, but revisits the keys that are in obj1 (not that it's likely to matter:

Object.keys(obj2).filter(key => key in obj1).forEach(key => {
    obj1[key] = obj2[key];
});

Since forEach ignores the return value of its callback, we could even go further in the concise-land:

Object.keys(obj2).filter(key => key in obj1).forEach(key => obj1[key] = obj2[key]);
like image 143
T.J. Crowder Avatar answered Oct 26 '22 07:10

T.J. Crowder


Here's a more functional approach using Array.prototype.reduce()

const obj1 = {
  "name": "",
  "age": ""
};

const obj2 = {
  "name": "Leo",
  "age": "14",
  "company": "aero",
  "shift": "night"
};

const newObject = Object.keys(obj1)
  .reduce(function(accumulator, key) {
    accumulator[key] = obj2[key]
    return accumulator
  }, {});

console.log(newObject);

Or some fun with ES6

const newObject = Object.keys(obj1)
  .reduce((a, key) => ({ ...a, [key]: obj2[key]}), {});
like image 32
jubalm Avatar answered Oct 26 '22 06:10

jubalm


Update 2020

const data = {a:1,b:2,b:3}
const form = {a:'',b:''}

for (const key in data) {
  if (key in form) {
    form[key] = data[key];
  }
}
console.log(form) // Output: {a:1,b:2}
like image 2
Aaron Tomlinson Avatar answered Oct 26 '22 07:10

Aaron Tomlinson