使用ES6将对象数组映射到带有标头的数组数组

时间:2017-06-02 17:19:51

标签: javascript arrays functional-programming ecmascript-6 concat

我想将我从后端的json响应获得的对象数组映射到数组数组,第一行是标题数组(标题)。我将使用此数组使其可以在csv文件中下载。

另外,我想要保留几个标题/列,这些标题/列对最终用户来说并不是真正有趣的csv文件。

我的代码工作正常,但我认为可以使用更简洁的代码完成。我很喜欢使用ES6 / ES2015,但我自己对扩展语法和其他ES6好东西没有经验,所以对于更好,更现代(功能/反应?)方法的任何建议都非常感激。

const originalData = [
  {name: 'Gizmo', species: 'cat', age: '9', raw: 'G9e76rd', updated_at: '1318874398806', skill: 'sleeping'},
  {name: 'Benny', species: 'dog', age: '3', raw: '98HDo2h', updated_at: '1318874392417', skill: 'chasing tail'},
  {name: 'Oscar', species: 'cat', age: '2', raw: '9da8Ro1', updated_at: '1318874390283', skill: 'meowing'}
]

let headers = []
const firstRow = originalData[0]
for (var key in firstRow) {
  if (firstRow.hasOwnProperty(key)) {
    if (!['raw','updated_at'].includes(key)) {
      headers.push(key)
    }
  }
}

const d = originalData.map(function(_, i) {
  return headers.map(function(header) {
    return originalData[i][header]
  }.bind(this))
}.bind(this))

const result = [headers].concat(d)

console.log(result)

8 个答案:

答案 0 :(得分:1)

这样的东西?

const originalData = [
  { name: 'Gizmo', species: 'cat', age: '9', raw: 'G9e76rd', updated_at: '1318874398806', skill: 'sleeping' },
  { name: 'Benny', species: 'dog', age: '3', raw: '98HDo2h', updated_at: '1318874392417', skill: 'chasing tail' },
  { name: 'Oscar', species: 'cat', age: '2', raw: '9da8Ro1', updated_at: '1318874390283', skill: 'meowing' }
]

const headers = Object.keys(originalData[0]).filter(key => !['raw', 'updated_at'].includes(key));
const d = originalData.map(obj => headers.map(key => obj[key]))
const result = [headers, ...d];

console.log(result)

答案 1 :(得分:1)

基本上你可以在过滤后的键上使用闭包,并对数组进行映射和连接。



const fn = (array => (keys => [keys].concat(array.map(o => keys.map(k => o[k]))))
           (Object.keys(array[0]).filter(k => !['raw','updated_at'].includes(k)))),
      data = [{ name: 'Gizmo', species: 'cat', age: '9', raw: 'G9e76rd', updated_at: '1318874398806', skill: 'sleeping' }, { name: 'Benny', species: 'dog', age: '3', raw: '98HDo2h', updated_at: '1318874392417', skill: 'chasing tail' }, { name: 'Oscar', species: 'cat', age: '2', raw: '9da8Ro1', updated_at: '1318874390283', skill: 'meowing' }],
      result = fn(data);


console.log(result);

.as-console-wrapper { max-height: 100% !important; top: 0; }




答案 2 :(得分:0)

你的很好。您可以使用Object.keys

简化标头创建
const originalData = [
  {name: 'Gizmo', species: 'cat', age: '9', raw: 'G9e76rd', updated_at: '1318874398806', skill: 'sleeping'},
  {name: 'Benny', species: 'dog', age: '3', raw: '98HDo2h', updated_at: '1318874392417', skill: 'chasing tail'},
  {name: 'Oscar', species: 'cat', age: '2', raw: '9da8Ro1', updated_at: '1318874390283', skill: 'meowing'}
]

const headers = Object.keys(originalData[0])
    .filter(key => !['raw','updated_at'].includes(key)));  
const data = originalData.map(row => headers.map(header => row[header]));

console.log(headers, data);

答案 3 :(得分:0)

const originalData = [
  {name: 'Gizmo', species: 'cat', age: '9', raw: 'G9e76rd', updated_at: '1318874398806', skill: 'sleeping'},
  {name: 'Benny', species: 'dog', age: '3', raw: '98HDo2h', updated_at: '1318874392417', skill: 'chasing tail'},
  {name: 'Oscar', species: 'cat', age: '2', raw: '9da8Ro1', updated_at: '1318874390283', skill: 'meowing'}
];

const propertiesNeeded = Object.keys(originalData[0]).filter(prop => !['raw', 'updated_at'].includes(prop));
const dataMapped = originalData.map(obj => propertiesNeeded.map(prop => obj[prop]));
const finalArr = [propertiesNeeded, ...dataMapped];

答案 4 :(得分:0)

尝试使用Array#map来重新创建包含Object.keyvalue的数组。和new Set()方法用户创建密钥集值。重复一个... spread syntax

const originalData = [
  {name: 'Gizmo', species: 'cat', age: '9', raw: 'G9e76rd', updated_at: '1318874398806', skill: 'sleeping'},
  {name: 'Benny', species: 'dog', age: '3', raw: '98HDo2h', updated_at: '1318874392417', skill: 'chasing tail'},
  {name: 'Oscar', species: 'cat', age: '2', raw: '9da8Ro1', updated_at: '1318874390283', skill: 'meowing'}
]

var result = [[...new Set(...originalData.map(a=> Object.keys(a)))]].concat(originalData.map(a=> Object.values(a)))

console.log(result)
.as-console-wrapper { max-height: 100% !important; top: 0; }

答案 5 :(得分:0)

我就是这样做的。我想如果你知道你在追求哪些钥匙,那么我们就可以充分利用它。

const data = [
  {name: 'Gizmo', species: 'cat', age: '9', raw: 'G9e76rd', updated_at: '1318874398806', skill: 'sleeping'},
  {name: 'Benny', species: 'dog', age: '3', raw: '98HDo2h', updated_at: '1318874392417', skill: 'chasing tail'},
  {name: 'Oscar', species: 'cat', age: '2', raw: '9da8Ro1', updated_at: '1318874390283', skill: 'meowing'}
]

const desiredKeys = ['name', 'species', 'age', 'skill']

const result = [desiredKeys].concat(data.map(pet => desiredKeys.map(key => pet[key])))

console.log(result)

答案 6 :(得分:0)

我想指出一个对象的按键顺序并没有完全由规范“修复”。

如果originalData中的第一只动物以species属性开头,则整个表格将按照列顺序进行格式化...

因此,我建议您在数组中明确定义列, 的顺序非常重要。

请注意,在下面的示例中,我交换了Gizmo的属性声明顺序。将这些数据放在您自己的代码中,第一列将是物种。 (至少在我的浏览器中,我猜它甚至可以在浏览器之间有所区别?)

const data = [
  {species: 'cat', name: 'Gizmo', age: '9', raw: 'G9e76rd', updated_at: '1318874398806', skill: 'sleeping'},
  {name: 'Benny', species: 'dog', age: '3', raw: '98HDo2h', updated_at: '1318874392417', skill: 'chasing tail'},
  {name: 'Oscar', species: 'cat', age: '2', raw: '9da8Ro1', updated_at: '1318874390283', skill: 'meowing'}
]


const getProps = props => obj => 
  props.map(k => obj[k]);
  
const columns = ["name", "species", "age", "skill"];

console.log(
  [columns, ...data.map(getProps(columns))]
);

答案 7 :(得分:0)

使用过滤器和reduce的完整链中的单行代码。

var unborken = chain => chain.filter((_, i, xx) => 
delete xx[i].updated_at && delete xx[i].raw).reduce((aac, _, i, aa) => 
(i === 0 ? aac.push(Object.keys(aa[i])) && aac.push(Object.values(aa[i])) :
aac.push(Object.values(aa[i])), aac), []);

const originalData = [{
    name: 'Gizmo',
    species: 'cat',
    age: '9',
    raw: 'G9e76rd',
    updated_at: '1318874398806',
    skill: 'sleeping'
  },
  {
    name: 'Benny',
    species: 'dog',
    age: '3',
    raw: '98HDo2h',
    updated_at: '1318874392417',
    skill: 'chasing tail'
  },
  {
    name: 'Oscar',
    species: 'cat',
    age: '2',
    raw: '9da8Ro1',
    updated_at: '1318874390283',
    skill: 'meowing'
  }
];


console.log(unborken(originalData));
.as-console-wrapper { max-height: 100% !important; top: 0; }