2013-10-04 254 views
0

我有一种情况,即需要将两个对象一起压缩以保留两个值。我可以遍历这两个对象并构建一个所有键的数组。从嵌套属性数组中获取对象嵌套值

var traverse = function (obj, chain) { 

     for (var prop in obj) { 
      if (obj.hasOwnProperty(prop)) { 

       var tempChain = [].concat(chain || []); 
       tempChain.push(prop); 

       if (typeof obj[prop] === 'object') { 
        traverse(obj[prop], tempChain); 
       } 
       console.log(tempChain); 
      } 
     } 
    }; 

传递如下所示:

traverse({ 
     'a': { 
      'b': 'hello world', 
      'b1': 'hello world 1', 
      'c': { 
       'd': 'dello' 
      } 
     } 
    }) 

会回到我:

[a] 
[a,b] 
[a,b1] 
[a,c] 
[a, c, d] 

所以我现在有嵌套属性的对象数组。我如何访问本质obj [[a,c,d]]?我知道我可以通过eval解决问题,但我无法相信内容。

eval('window.' + ['a','c','d'].join('.')); 

如果可以通过阵列环,并检查,以查看是否在两者存在属性,然后生成的组合“拉链”值的新对象。

+0

'窗口== obj',这不会反正工作。但是,是的,你可以使用一个简单的循环。 – Bergi

+0

检查[任何这些重复](http://stackoverflow.com/a/14397052/1048572) - 只是省略'.split(“。”)''因为你已经有一个数组 – Bergi

+0

我认为这是某种[XY问题](http://meta.stackexchange.com/questions/66377/what-is-the-xy-problem)。你的'zip'应该做什么,为什么你需要物业链? – Bergi

回答

1

也许像这样?

function getValueAt(obj, keyPathArray) { 
    var emptyObj = {}; 

    return keyPathArray.reduce(function (o, key) { 
     return (o || emptyObj)[key]; 
    }, obj); 
} 

然后你可以使用它像:

var o = { a: { c: { d: 1 } } }; 

getValueAt(o, ['a', 'c', 'd']); //1 

但是它是不存在的性能效率不高,因为它不会短路。 这里是不使用reduce另一种方法:

function getValueAt(o, keyPathArray) { 
    var i = 0, 
     len = keyPathArray.length; 

    while (o != null && i < len) o = o[keyPathArray[i++]]; 

    return o;  
} 
+0

为什么不简单'while(o!= null && i Bergi

+0

我试过使用这两个你的解决方案,但是该函数返回值,我想指向该值的对象。为了给出一个更好的解释继承人一些正在使用evals的工作代码。 http://jsbin.com/EHeFayu/7/ – dtsn

+0

@Bergi,是的,不知何故,我没有把最后一个值作为一个对象,而'null'类型是'对象'。愚蠢的错误。固定。 – plalx