【问题标题】:Tricky object flattening棘手的对象展平
【发布时间】:2020-07-03 21:35:41
【问题描述】:

我真的不想重新发明自行车,所以当你有这样的对象时,也许有人已经遇到过这种情况:

{
   a: {
      site1: {
         type1: {
            item1: 42,
            item2: 13
         }
      },
      site2: {
         type2: {
            item3: 35
         }
      }
   }
}

你需要把它放入一个数组中:

[
   [ a, site1, type1, 42],
   [ a, site1, type1, 13],
   [ a, site2, type2, 35]
]

【问题讨论】:

  • 您不需要 42、13 等...吗?或者你的意思是你想要最终数组中的值(而不是键)?
  • 这是递归树遍历。
  • @BrettGregson,你是对的,我需要号码而不是 itemN

标签: javascript object flatten


【解决方案1】:

您需要在树中递归:

const data = {
  a: {
    site1: {
      type1: {
        item1: 42,
        item2: 13,
      },
    },
    site2: {
      type2: {
        item3: 35,
      },
    },
  },
};

function walk(data, out, path = []) {
  Object.keys(data).forEach(key => {
    const newPath = [...path, key];
    const value = data[key];
    if (typeof value === "object") {
      walk(value, out, newPath);
    } else {
      out.push([newPath, value]);
      // Or if you really don't need the value...
      //out.push(newPath);
    }
  });
}

const out = [];
walk(data, out);
console.log(out);

输出

[
  [ [ 'a', 'site1', 'type1', 'item1' ], 42 ],
  [ [ 'a', 'site1', 'type1', 'item2' ], 13 ],
  [ [ 'a', 'site2', 'type2', 'item3' ], 35 ]
]

通过更改已注释掉的那一行,您可以获得您最初想要的结果,而无需值。

【讨论】:

    【解决方案2】:

    这里有一个更简单的解决方案:

    function flattenObject(objToFlat, path = []) {
      return Object.keys(objToFlat).reduce(
        (result, key) => [
          ...result,
          ...(typeof objToFlat[key] === 'object'
            ? flattenObject(objToFlat[key], [...path, key])
            : [[...path, objToFlat[key]]]),
        ],
        []
      );
    }
    

    请注意,您不需要将空数组传递给函数。

    您可以在这个 plunker 中测试解决方案:http://plnkr.co/edit/IM5v3fyAMrfV5HKS?open=lib%2Fscript.js

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2014-01-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-03-05
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多