Storing Tree Structures in JSON
I'm trying to write a system where the client (browser-based) requests a tree to be returned from the server (app engine, but that's irrelevant). The problem is in converting the tree to JSON: because each object refers to the objects 'below' it, when stringified I end up with an extremely long string which, on parsing, creates new objects for each child instead of references to other nodes.
My current solution would be to write an 'equalTo' and 'toString' function (converting object references to strings) stringify the resulting array and then recreate it on the client side by resolving strings to objects. That solution is making my terrible-algorithm-senses tingle, though, there must be a better way to return such structures through JSON!
EDIT: it just occurred to me that object references could also be converted to array indexes. It's a better solution, but still has that niggling bad-code fee开发者_如何学JAVAl to it.
EDIT2: Right, so I suppose some pseudo-code is in order, then.
var node = {
children : null;
};
var root = Object.create(node);
var level1a = Object.create(node);
var level1b = Object.create(node);
var level2a = Object.create(node);
var level2b = Object.create(node);
root.children = [level1a, level1b];
level1a.children = [level2a, level2b];
So you end up with a tree that looks like this: stackoverflow won't let me post images
If you have a way to address nodes, you can use JSON revivers and replacers to convert between addresses and references.
For example, if you have two functions like
function addressForNode(node) { ... }
function nodeForAddress(address) { ... }
you could use revivers and replacers that call those when parsing or stringifying
var jsonString = JSON.stringify(tree, function (key, value) {
if (typeof value === 'object') {
var address = addressForNode(value);
if (address !== null) { // value really is a node
return { address: address }
}
}
return value;
});
// And to parse...
var tree = JSON.parse(jsonString, function (key, value) {
if (typeof value === 'object' && typeof value.address === 'string') {
return nodeForAddress(value.address);
}
return value;
});
If you can help it, don't restrict yourself to JSON. Instead consider generating JavaScript code included via linked script, using JSONP techniques if necessary.
精彩评论