从对象形成数据集

时间:2019-08-14 11:48:26

标签: javascript performance ecmascript-6

我正在尝试从一个对象构造数据集,该对象是我从API收到的响应。

数据采用格式。

let assets = [
  {count: 1, skills: ["teach", "play"]},
  {count: 1, skills: ["write", "surf"]},
  {count: 2, skills: ["run", "teach"]},
  {count: 3, skills: ["teach", "run", "hike"]}
]

通过以上回复形成一系列独特的技能。

let unique = ["teach", "play", "write", "surf", "run", "hike"]

我通过运行构造了一个对象数组。

let finalObj = {};
unique.map( (skill) => {
  finalObj[skill] = assets.filter( asset => asset.skills.includes(skill) )
  .map( asset => ({skill: skill, count: asset.count}) );  
})

这是运行代码后的样子。

也许这是一个可以避免的额外步骤。

finalObj = {
  teach: [{skill: teach, count: 1},{skill: teach, count: 2}, {skill: teach, count: 3}],
  play: [{skill: play, count: 1}],
  write: [{skill: write, count: 1}],
  surf: [{skill: surf, count: 1}],
  run: [{skill: run, count: 2}, {skill: run, count: 3}],
  hike: [{skill: hike, count: 3}]
}

我希望我的最终数据是。

let data0 = [ 
  {skill: 'teach', count: 2},
  {skill: 'play', count: 1},
  {skill: 'write', count: 1},
  {skill: 'surf', count: 1},
  {skill: 'run', count: 2},
  {skill: 'hike', count: 3}
]

let data1 = [
  {skill: 'teach', count: 2},
  {skill: 'run', count: 3}
]

let data2 = [
  {skill: teach, count: 3}
]

// To find the max length of all array in finalObj
let tempLen = 0;
Object.keys(finalObj).forEach((key) => {
  if (tempLen > finalObj[key].length) {
    tempLen = tempLen
  } else {
    tempLen = finalObj[key].length
  }
})
// returns 3 - expected

这是显示一种在for循环内创建变量的方法,该循环使用变量名中的当前迭代值。与实际代码无关。

for (let i = 0; i < tempLen; i++) {
  let str ="data"+ i+" = []";
  eval(str).push(i)
}
// returns data0=[0], data1=[1], data2=[2] - expected

这表明通过硬编码变量名和数组索引可以达到预期的结果。我的应用程序中没有这种情况。

let sampleData = []
Object.keys(finalObj).forEach(key => 
  sampleData.push(finalObj[key][0])
)
// returns expected data

在实际情况下尝试使用此方法。

for (let i = 0; i < tempLen; i++) {
  let str ="data"+ i+" = []";
  Object.keys(finalObj).forEach((key) => {
    eval(str).push(finalObj[key][i])
  })
}
// not expected result

1 个答案:

答案 0 :(得分:0)

我使用data对象存储所需的数组,在该对象的键迭代中,将进行检查来避免使用undefined元素。您需要避免使用eval

let assets = [{
    count: 1,
    skills: ["teach", "play"]
  },
  {
    count: 1,
    skills: ["write", "surf"]
  },
  {
    count: 2,
    skills: ["run", "teach"]
  },
  {
    count: 3,
    skills: ["teach", "run", "hike"]
  }
];

let unique = ["teach", "play", "write", "surf", "run", "hike"];

let finalObj = {};
unique.map((skill) => {
  finalObj[skill] = assets.filter(asset => asset.skills.includes(skill))
    .map(asset => ({
      skill: skill,
      count: asset.count
    }));
});

let tempLen = 0;
Object.keys(finalObj).forEach((key) => {
  if (tempLen > finalObj[key].length) {
    tempLen = tempLen
  } else {
    tempLen = finalObj[key].length
  }
})

let data = {};

for (let i = 0; i < tempLen; i++) {
  data["data" + i] = [];
  Object.keys(finalObj).forEach((key) => {
    if (finalObj[key][i])
      data["data" + i].push(finalObj[key][i])
  })
}

console.log(data);