通过计算将对象数组转换为数组

时间:2019-02-01 13:05:52

标签: javascript arrays object

我正在使用以下对象数组,并尝试将其转换为数组:

const data = [
  {
    count: 3,
    userName: "Paul Crewe",
    value: "Activity Type",
  },
  {
    count: 1,
    userName: "Nate Scarborough",
    value: "Activity Type",
  },
  {
    count: 1,
    userName: "Nate Scarborough",
    value: "Another Activity Type",
  },
  {
    count: 1,
    userName: "Paul Crewe",
    value: "Another Activity Type",
  },
];

预期结果:

const outcome = [
  ['userName', 'Paul Crewe', 'Nate Scarborough'],
  ['Activity Type', 3, 1],
  ['Another Activity Type', 1, 1]
];

结果数组获取数据,并使用userName键创建第一个数组元素,然后创建valuecount格式,用于每个其他数组元素。例如,

['userName', 'Paul Crewe', 'Nate Scarborough'],
[{value}, {count for Paul Crewe}, {count for Nate Scarborough} ],

我认为使用reduce是合适的,并且开始于:

data.reduce((a, c) => {
  a[c.userName] = { value: c.value, count: c.count };
  a[c.userName].count += c.count;
  return a;
}, {});

但这会导致不希望的结果,例如:

{
  Nate Scarborough: {value: "Another Activity Type", count: 2},
  Paul Crewe: {value: "Another Activity Type", count: 2},
}

2 个答案:

答案 0 :(得分:1)

您可以从键userName开始,并根据需要构建新的值行。它可以处理任意数量的值。

此解决方案可以返回稀疏数组的数组。如果不需要,则需要将内部数组映射为默认零。

const
    data = [{ count: 3, userName: "Paul Crewe", value: "Activity Type" }, { count: 1, userName: "Nate Scarborough", value: "Activity Type" }, { count: 1, userName: "Nate Scarborough", value: "Another Activity Type" }, { count: 1, userName: "Paul Crewe", value: "Another Activity Type" }],
    result = data.reduce((r, o) => {
        var vIndex = r.findIndex(([v]) => v === o.value),
            index = r[0].indexOf(o[r[0][0]]);

        if (vIndex < 0) {
            vIndex += r.push([o.value]);
        }            
        if (index < 0) {
            index += r[0].push(o[r[0][0]]);             
        }
        r[vIndex][index] = (r[vIndex][index] || 0) + o.count;
        return r;
    }, [['userName']]);

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

答案 1 :(得分:0)

在处理数组时,我有点老套-比起各种“奇特的”数组方法,我更喜欢自己做循环。

这是我的处理方式,

const data = [
      {
        count: 3,
        userName: "Paul Crewe",
        value: "Activity Type",
      },
      {
        count: 1,
        userName: "Nate Scarborough",
        value: "Activity Type",
      },
      {
        count: 1,
        userName: "Nate Scarborough",
        value: "Another Activity Type",
      },
      {
        count: 1,
        userName: "Paul Crewe",
        value: "Another Activity Type",
      },
    ];
    
    const temp = {
      userName : []
    };
    
    data.forEach(function(e) {
      // push username only if not in array already
      if(temp.userName.indexOf(e.userName) === -1) {
        temp.userName.push(e.userName);
      }
      // create empty array for activity name, if not exists yet
      if(!temp[e.value]) {
        temp[e.value] = [];
      }
      temp[e.value].push(e.count)
    });
    
    var outcome = [];
    // special treatment for userName, to make sure that comes first
    temp.userName.unshift('userName');
    outcome.push(temp.userName);
    
    for(k in temp) {
      if(k != 'userName') {
        temp[k].unshift(k); // insert activity name at front of array
        outcome.push( temp[k]); // insert array into final result array
      }
    }
    console.log(outcome)

使用temp辅助对象可以更轻松地使用活动名称访问正确的数组-如果我直接使用所需的结构,那将意味着遍历数组并一直比较第一个条目,以找到合适的对象,而使用对象进行简单的属性查找即可。