1

Here is my fiddle : DEMO

By recursive iterations, I am able to find the key in object2 object3 and replace its value by the values from data2 data3 objects.

However, I am unable to replace the value if it is an array. (key called 'coordinates' in this case) How could this be fixed?

function update(object, data) {
  function getAllKeys(o) {
    Object.keys(o).forEach(function(k) {
      if (typeof o[k] === 'object') {
        return getAllKeys(o[k]);
      }
      keys[k] = o;
    });
  }
  var keys = Object.create(null);
  getAllKeys(object);
  Object.keys(data).forEach(function(k) {
    if (keys[k] && k in keys[k]) { // check if key for update exist
      keys[k][k] = data[k];
    }
  });
}

3 Answers 3

2

Update the getAllKeys method with:

  function getAllKeys(o) {
    Object.keys(o).forEach(function(k) {
      contains_object = Array.isArray(o[k]) && o[k].some(val=> { return typeof val == "object" && !Array.isArray(val);  });
      if ((Array.isArray(o[k]) && !contains_object)  || typeof o[k] !== 'object') {
        keys[k] = o;
      } else {
        return getAllKeys(o[k]);
      }
      keys[k] = o;
    });
  }

Note: !(o[k] instanceof Array) - http://jsfiddle.net/08pnu7rx/1/

Sign up to request clarification or add additional context in comments.

3 Comments

Hey thanks! It worked for object2 & object3 but fails for this one. Please check :jsfiddle.net/inchrvndr/fL4ectvy
Brilliant! Thanks :D
Hey, many thanks for the solution. Although this is an old post, just a small addition: If the property has a null value then we get error, that's why we need to add: || o[k] === null within if condition in the getAllKeys() function
0

The problem is that typeof also returns object for arrays.

You want to change your function to still assign the key when the object is an array.

function getAllKeys(o) {
  Object.keys(o).forEach(function(k) {
    if (Array.isArray(o[k]) || typeof o[k] !== 'object') {
      keys[k] = o;
    } else {
      return getAllKeys(o[k]);
    }
  });
}

Notice I swapped around the logic, so you first check for either an array or another non-object type. If that check passes, you assign the value. If not, you recurse.

You should note that this is not at all specific to arrays. You will have similar problems if you have a nested property that is a Date, for example.

1 Comment

Hi, it worked for object2, object but not for this one, please check jsfiddle.net/inchrvndr/fL4ectvy/5
0

The problem in your code is that typeof o[k] === 'object' returns true even it o[k] is an array which is the case for coordinated, You need a negative check for array too like

Object.keys(o).forEach(function(k) {
  if (typeof o[k] === 'object'&& !Array.isArray(o[k])) {
    return getAllKeys(o[k]);
  }
  keys[k] = o;
});

Working fiddle

According to the docs or typeof:

// use Array.isArray or Object.prototype.toString.call
// to differentiate regular objects from arrays
typeof [1, 2, 4] === 'object';

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.