使用javascript获取每个级别的json值

使用javascript获取每个级别的json值,javascript,json,Javascript,Json,我正在尝试使用递归函数从一个简单的json使用javascript 我有一个jsonjson: { 'a': { 'b': { 'c': 12, 'd': 'Hello World' }, 'e': [1,2,3] } } 我的预期结果是: { 'a/b/c': 12, 'a/b/d': 'Hello World', 'a/e': [1,2,3] } 我正在尝试: function getDeepKeys(obj) {

我正在尝试使用递归函数从一个简单的
json
使用
javascript

我有一个json
json

{
  'a': {
    'b': {
      'c': 12,
      'd': 'Hello World'
    },
    'e': [1,2,3]
  }
}
我的预期结果是:

{
  'a/b/c': 12,
  'a/b/d': 'Hello World',
  'a/e': [1,2,3]
}
我正在尝试:

function getDeepKeys(obj) {
    var keys = [];
    for (var key in obj) {
        keys.push(key);
        if (typeof obj[key] === "object") {
            var subkeys = getDeepKeys(obj[key]);
            keys = keys.concat(subkeys.map(function (subkey) {
                return key + "/" + subkey;
            }));
        }
    }
    return keys;
} 
但出于某种原因,它让我回想起:

a/b/c/d/e/0/1/
,我不知道它为什么要在那里添加这些数字。
有人对我怎么做有想法吗?

我想你可能把事情弄得太复杂了。您可以使用
array.isArray
和非对象(
typeof!==“object
)测试数组,然后只返回路径和值。否则,将为每个条目递归
reduce()
就是这样。将当前路径作为参数传递给递归函数也很方便:

let obj={'a':{'b':{'c':12,'d':'Hello World'},'e':[1,2,3]}
函数getValues(obj,路径=[])){
return(Array.isArray(obj)| | typeof obj!=“object”)
?{[path.join('/')]:obj}
:Object.entries(obj).reduce((acc,[key,val])=>
赋值(acc,getValues(val,path.concat(key)))
, {})
}

console.log(getValues(obj))
您可以使用函数
Object.keys
来循环对象的键,通过递归,您可以更深入地遍历嵌套对象

让obj={'a':{'b':{'c':12,'d':'helloworld'},'e':[1,2,3]},
结果=对象。创建(空),
循环=功能(o、arr、结果){
Object.keys(o.forEach)(k=>{
arr.push(k);
if(typeof o[k]=“object”&&&!Array.isArray(o[k]))循环(o[k],arr,result);
else结果[arr.join('/')]=o[k];
arr.拼接(-1);
});
};    
循环(obj,[],结果);
控制台日志(结果)

.as console wrapper{max height:100%!important;top:0;}
您可以使用显式堆栈进行迭代,该堆栈的开销小于递归,并且不会破坏调用堆栈:

constpathify=o=>{
常量路径={};
常量堆栈=[[o,[]];
while(堆栈长度){
const[curr,path]=stack.pop();
for(常数k,当前值){
if(当前[k]的类型=“对象”&&!Array.isArray(当前[k])){
stack.push([curr[k],path.concat(k)];
}
否则{
路径[`${path.join(“/”)}/${k}`]=curr[k];
}
}
}
返回路径;
};

log(pathify({'a':{'b':{'c':12,'d':'helloworld'},'e':[1,2,3]})我可以通过将if条件更改为
if(typeof obj[key]==“object”&&!Array.isArray(obj[key]))来修复它。
。似乎我们需要防止代码下降到数组中。但我不能100%确定这将涵盖所有可能的情况。为什么要创建一个不从
object
继承的对象呢。这似乎会导致意想不到的行为?例如,您应该能够调用
result.hasOwnProperty()
,但如果您使用
Object.create(null)
@MarkMeyer对其进行中性化,则不能调用它。我这样创建一个对象,因为我知道这种方法只需要具有特定键的对象,所以调用
.hasOenProperty()
不是问题。我很感兴趣的是,这样做是否比得到一个没有标准对象行为的对象更有好处。这是一种很好(而且很快)的方法(尽管它必须是一个相当大的对象才能破坏调用堆栈)。