Javascript Reference

Javascript的赋值操作就是引用修改,举个例子:

reference.jsgrunt-properties
1
2
3
4
5
6
7
8
9
10
11
12
13
function splitKeys(obj, splitter) {
var keys, value, parent, result = {};
for (var key in obj) {
keys = key.split(splitter);
value = obj[key].replace(/"/g, '\\"');
parent = result;
for (var j = 0; j < keys.length-1; j++) {
parent = parent[keys[j]] = parent[keys[j]] || {};
}
parent[keys[keys.length-1]] = value;
}
return JSON.stringify(result, null, 2);
}

这段代码将Java程序中的常见的Properties文件中的键值映射成了嵌套的JSON对象:

test.js
1
2
3
4
5
6
7
8
9
10
var obj = {"country.province.city": "Chengdu"};
splitKeys(obj, '.');

-> "{
"country": {
"province": {
"city": "Chengdu"
}
}
}"

我们从实现代码的这行开始看起parent = result;,很简单地把parent指向result这个空对象。

再看接下来的代码,也是最巧妙的地方:

parts
1
2
3
for (var j = 0; j < keys.length-1; j++) {
parent = parent[keys[j]] = parent[keys[j]] || {};
}

第一次循环:
parent开始是空对象,parent = parent['country'] = parent['country'] || {};,将会生成一个parent的country属性,该属性的值还是一个空对象。于此同时,parent会指向新生成的、也即它的country属性。

第二次循环:
parent指向了country,parent = parent['province'] = parent['province'] || {};也即parent = country['province'] = country['province'] || {};,此时,将会生成一个country的province属性,该属性的值还是一个空对象,而parent则指向了province对象。

所以 parent[keys[keys.length-1]] = value;等价为province['city'] = "Chengdu";

最后,return JSON.stringify(result, null, 2);,这最后的result就是具有嵌套效果的JSON对象了。