Reputation: 5929
In this recursive function, I want to replace a value inside a (nested) object.
var testobj = {
'user': {
'name': 'Mario',
'password': 'itseme'
}
};
updateObject('emesti', 'password', testobj)
function updateObject(_value, _property, _object) {
for(var property in _object) {
if(property == _property) {
_object[property] = _value;
}
else if(objectSize(_object) > 0) {
updateObject(_value, _property, _object[property]);
}
}
return _object
};
function objectSize(_object) {
var size = 0, key;
for (key in _object) {
if (_object.hasOwnProperty(key)) size++;
}
return size;
};
After running this, firefox throws the exception "too much recursion" on the line else if(objectSize(_object) > 0) {
.
Edit: if I set
function updateObject(_value, _property, _object) {
for(var property in _object) {
if(property == _property) {
_object[property] = _value;
}
else if(_object[property].hasOwnProperty(_property)) {
updateObject(_value, _property, _object[property]);
}
}
return _object
};
it works, but it only searches one level. If I had an nested object inside a nested object, it wouldn't work.
Any more ideas?
Edit: This problem occurs in Firefox 3.6. It works in Chrome.
Upvotes: 3
Views: 3142
Reputation: 383716
I'm not 100% familiar with how to do things in Javascript, but essentially you want something like this:
var testobj = {
'user': {
'name': 'Mario',
'password': 'itseme',
'bleh': {
'password': 'something'
}
}
};
function updateObject(_value, _property, _object) {
for(var property in _object) {
if(property == _property) {
_object[property] = _value;
}
else if(explorable(_object[property])) {
updateObject(_value, _property, _object[property]);
}
}
return _object
};
function explorable(_object) {
return typeof(_object) != "string";
};
updateObject('emesti', 'password', testobj);
document.writeln(testobj.user.password); // "emesti"
document.writeln(testobj.user.bleh.password); // "emesti"
Currently, anything that isn't a string is explorable
. This may or may not work for all cases, so you may want to use a better definition of what is explorable
.
Also note that the recursion right now updates ALL matching properties.
Upvotes: 4
Reputation: 413702
Here's an idea:
function updateObject(_value, _property, _object) {
function u(v, p, o) {
if (o === _object) return;
if (o.hasOwnProperty(p))
o[p] = v;
else {
for (var prop in o)
if (o.hasOwnProperty(prop))
u(v, p, o[prop]);
}
}
u(_value, _property, _object);
return _object
};
That adds a test to make sure you don't start over back at the original object.
Upvotes: 0
Reputation: 1170
You're not using .hasOwnProperty()
in the for loop inside updateObject
. Could it be finding some kind of in-built property which is essentially "infinite" in depth?
Upvotes: 1
Reputation: 19475
shouldn't if(objectSize(_object) > 0) {
be if(objectSize(_object[property]) > 0) {
?
Upvotes: 1