This is a reverse question to this question.
Given an object x={a:1,b:2}
and a string c.d=3
, modify object x to the following:
Had to do something similar today, here's another solution. Definitely could use some cleanup, but it does the trick. This will extend an existing object and won't wipe any data provided the input is valid.
There's no validation, so you can definitely overwrite keys if you pass it bad data.
// @param object orig the object to extend
// @param array keyParts the.key.path split by "." (expects an array, presplit)
// @param mixed value the value to assign
// @param object scoped used by the recursion, ignore or pass null
function unflatten(orig, keyParts, value, scoped) {
if (!scoped) {
scoped = orig;
}
var nextKey = keyParts.shift();
if (keyParts.length === 0) {
scoped[nextKey] = value;
return orig;
}
if (!scoped[nextKey]) {
scoped[nextKey] = {};
}
scoped = scoped[nextKey];
return unflatten(orig, keyParts, value, scoped);
}
The function prototype can be improved, but serves my needs. Call it via:
var orig = { foo: 'hello world', bar: { baz: 'goodbye world' } };
// lets add the key "bar.cat.aww" with value "meow"
unflatten(orig, "bar.cat.aww".split("."), "meow");
/*
orig is {
foo: "hello world",
bar: {
baz: "goodbye world",
cat: {
aww: "meow"
}
}
}
*/
// we can keep calling it to add more keys
unflatten(orig, "some.nested.key".split("."), "weeee");
/*
orig is {
foo: "hello world",
bar: {
baz: "goodbye world",
cat: {
aww: "meow"
}
},
some: {
nested: {
key: "weeee"
}
}
}
*/