从深层嵌套对象中获取值

时间:2017-11-15 08:16:36

标签: javascript google-apps-script

我正在努力从深层嵌套的对象中获取值。数据和预期产量如下。我从API的请求中得到了如下数据。

我必须在Google Apps脚本中使用此脚本。所以请注意我不能使用ECMAScript6。

对象

var obj = {
  "key1": [
    {
      "key2": [
        {
          "key3": {
            "key4": {
              "key5": [
                {
                  "key6": "value6"
                },
                {},
                {
                  "key7": {
                    "key8": "value8"
                  }
                }
              ]
            }
          }
        },
        {
          "key3": {
            "key4": {
              "key5": [
                {
                  "key6": "value6"
                },
                {
                  "key7": {
                    "key8": "value8"
                  }
                },
                {}
              ]
            }
          }
        },
        {
          "key3": {
            "key5": "value5"
          }
        }
      ]
    },
    {
      "key2": [
        {
          "key3": {
            "key4": {
              "key5": [
                {
                  "key6": "value6"
                },
                {
                  "key7": {
                    "key8": "value8"
                  }
                }
              ]
            }
          }
        },
        {
          "key3": {
            "key4": {
              "key5": [
                {
                  "key6": "value6"
                },
                {},
                {
                  "key7": {
                    "key8": "value8"
                  }
                },
                {}
              ]
            }
          }
        },
        {
          "key3": {
            "key5": "value5"
          }
        }
      ]
    }
  ]
};

预期输出

我想要“key8”的值。

value8
value8
value8
value8

我当前的剧本

for (var i in obj.key1) {
  for (var j in obj.key1[i].key2) {
    for (var k in obj.key1[i].key2[j].key3.key4.key5[k]) {
      Logger.log(obj.key1[i].key2[j].key3.key4.key5[k].key7.key8)
    }
  }
}

错误消息

TypeError: Cannot read property "key5" from undefined.

此错误发生在

for (var k in json.key1[i].key2[j].key3.key4.key5[k]) {

我的问题是

  • 错误的原因是什么?
  • 如何修改我的脚本以获取“key8”的值?

更新

我有两个问题的解决方案。

一个是

var result = [];
for (var i in obj.key1) {
  for (var j in obj.key1[i].key2){
    if (obj.key1[i].key2[j].key3.key4) {
      for (var k in obj.key1[i].key2[j].key3.key4.key5) {
        if (obj.key1[i].key2[j].key3.key4.key5[k].key7) {
          result.push(obj.key1[i].key2[j].key3.key4.key5[k].key7.key8);
        }
      }
    } else {
      continue;
    }
  }
}
Logger.log(result) // >>> [value8, value8, value8, value8]

https://jsfiddle.net/Lxa8tsfb/

另一个是

var result = function () {
  var result = [];
  (function traverse(obj) {
    if (Array.isArray(obj)) {
      obj.forEach(traverse);
    } else if (typeof obj === 'object') {
      Object.keys(obj).forEach(function(key) {
        if (key === 'key8') {
          result.push(obj[key]);
        } else {
          traverse(obj[key]);
        }
      });
    }
  }(obj));
  return result;
}();
Logger.log(result) // >>> [value8, value8, value8, value8]

https://jsfiddle.net/ffuuur0L/

第一个是我的回答。第二个是@Petr的答案。我的答案只有在用户知道对象的结构时才能使用。当用户知道密钥时,Petr的答案可以使用。我认为Petr的答案很有用。所以我接受了彼得的回答。

1 个答案:

答案 0 :(得分:0)

你可以在这里使用递归,如下所示:

function traverse(json) {
    if (Array.isArray(json)) {
        json.forEach(traverse);
    } else if (typeof json === 'object') {
        Object.keys(json).forEach(function(key) {
            if (key === 'key8') {
                console.log(json[key]);
            } else {
               traverse(json[key]);
            }
        });
    }
};

traverse(json);

这段代码显然不完美,您可能希望将key8作为一个参数并将其包装到一个名称更好的方法中,但它可以正常工作。