减少 javascript 中的对象数组

Reduce array of objects in javascript

我在 javascript 中有一组要减少的对象。请参阅下面的代码。 6 位数或更多数字的消息已验证,更少未验证。我按组分组。

const myArray = [
  { group: 'groupA', message: 'Text without a number', sl: '1A' },
  { group: 'groupA', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupB', message: 'Text without a number', sl: '1A' },
  { group: 'groupA', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupB', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupC', message: 'Text without a number', sl: '1B' },
  { group: 'groupD', message: 'Text with a number Tick0127866', sl: '1B' },
  { group: 'groupC', message: 'Text without a number', sl: '1A' }
];

output = myArray.reduce((acc, line) => {
  let yes = 0;
  let no = 0;

  line.message.match(/\d{6,}/) ? yes++ : no++;

  acc[line.group] = acc[line.group] || {};
  acc[line.group].verified = (acc[line.group].verified || 0) + yes;
  acc[line.group].unverified = (acc[line.group].unverified || 0) + no;
  return acc;
}, {});

console.log('output', output);

但是我希望输出也是一个对象数组,如下所示:

[
  { group: 'groupA', verified: 2, unverified: 1 },
  { group: 'groupB', verified: 1, unverified: 1 },
  { group: 'groupC', verified: 0, unverified: 2 },
  { group: 'groupD', verified: 1, unverified: 0 }
]

我该怎么做?

您可以在 Object.entries 上使用 map()。我还在 reduce 方法

中重构了您的代码

const myArray = [
  { group: 'groupA', message: 'Text without a number', sl: '1A' },
  { group: 'groupA', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupB', message: 'Text without a number', sl: '1A' },
  { group: 'groupA', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupB', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupC', message: 'Text without a number', sl: '1B' },
  { group: 'groupD', message: 'Text with a number Tick0127866', sl: '1B' },
  { group: 'groupC', message: 'Text without a number', sl: '1A' }
];

let output = myArray.reduce((acc, line) => {
  acc[line.group] = acc[line.group] || {verified: 0, unverified: 0};
  if(line.message.match(/\d{6,}/)){
    acc[line.group].verified++
  }
  else{
    acc[line.group].unverified++
  }

  return acc;
}, {});

output = Object.entries(output).map(([k, v]) => ({group: k, ...v}))

console.log('output', output);

groupprop 放入您的帐户中。 然后使用Object.values函数来return一个对象的值。

const myArray = [
  { group: 'groupA', message: 'Text without a number', sl: '1A' },
  { group: 'groupA', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupB', message: 'Text without a number', sl: '1A' },
  { group: 'groupA', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupB', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupC', message: 'Text without a number', sl: '1B' },
  { group: 'groupD', message: 'Text with a number Tick0127866', sl: '1B' },
  { group: 'groupC', message: 'Text without a number', sl: '1A' }
];

output = myArray.reduce((acc, line) => {
  let yes = 0;
  let no = 0;

  line.message.match(/\d{6,}/) ? yes++ : no++;

  acc[line.group] = acc[line.group] || {};
  acc[line.group].group = line.group;
  acc[line.group].verified = (acc[line.group].verified || 0) + yes;
  acc[line.group].unverified = (acc[line.group].unverified || 0) + no;
  return acc;
}, {});

console.log('output', Object.values(output));

您可以简单地扩展您的 solution/output 以使用 Object.entries()Object.keys() 获得实际需要的输出。我要使用 Object.entries()

const myArray = [
  { group: 'groupA', message: 'Text without a number', sl: '1A' },
  { group: 'groupA', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupB', message: 'Text without a number', sl: '1A' },
  { group: 'groupA', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupB', message: 'Text with a number WO5467829', sl: '1A' },
  { group: 'groupC', message: 'Text without a number', sl: '1B' },
  { group: 'groupD', message: 'Text with a number Tick0127866', sl: '1B' },
  { group: 'groupC', message: 'Text without a number', sl: '1A' }
];

output = myArray.reduce((acc, line) => {
  let yes = 0;
  let no = 0;

  line.message.match(/\d{6,}/) ? yes++ : no++;

  acc[line.group] = acc[line.group] || {};
  acc[line.group].verified = (acc[line.group].verified || 0) + yes;
  acc[line.group].unverified = (acc[line.group].unverified || 0) + no;
  return acc;
}, {});

console.log('output', output);

const actualOutput = Object.entries(output).map(([group, value]) => ({group, ...value }));

console.log(actualOutput);

使用数组作为累加器的初始值,在 .reduce 中,使用 findIndex 检查当前组,如果找到,更新 verifiedunverified 值,否则,插入一个新值:

const myArray = [
  { group: "groupA", message: "Text without a number", sl: "1A" },
  { group: "groupA", message: "Text with a number WO5467829", sl: "1A" },
  { group: "groupB", message: "Text without a number", sl: "1A" },
  { group: "groupA", message: "Text with a number WO5467829", sl: "1A" },
  { group: "groupB", message: "Text with a number WO5467829", sl: "1A" },
  { group: "groupC", message: "Text without a number", sl: "1B" },
  { group: "groupD", message: "Text with a number Tick0127866", sl: "1B" },
  { group: "groupC", message: "Text without a number", sl: "1A" }
];

output = myArray.reduce((acc, line) => {
  let yes = 0;
  let no = 0;

  line.message.match(/\d{6,}/) ? yes++ : no++;

  // check if you have the group in the accumulator
  const ndx = acc.findIndex(e => e.group === line.group);

  // if you have it, manipulate verified and unverified
  if (ndx > -1) {
    acc[ndx].verified = (acc[ndx].verified || 0) + yes;
    acc[ndx].unverified = (acc[ndx].unverified || 0) + no;
  } else {
    // insert a new entry instead
    acc.push({
      group: line.group,
      verified: yes,
      unverified: no
    });
  }

  return acc;
}, []); // use an array as the initial value of the accumulator

console.log(output);

像这样将 reduce 与正则表达式测试结合使用 -

const myArray = [{
    group: 'groupA',
    message: 'Text without a number',
    sl: '1A'
  },
  {
    group: 'groupA',
    message: 'Text with a number WO5467829',
    sl: '1A'
  },
  {
    group: 'groupB',
    message: 'Text without a number',
    sl: '1A'
  },
  {
    group: 'groupA',
    message: 'Text with a number WO5467829',
    sl: '1A'
  },
  {
    group: 'groupB',
    message: 'Text with a number WO5467829',
    sl: '1A'
  },
  {
    group: 'groupC',
    message: 'Text without a number',
    sl: '1B'
  },
  {
    group: 'groupD',
    message: 'Text with a number Tick0127866',
    sl: '1B'
  },
  {
    group: 'groupC',
    message: 'Text without a number',
    sl: '1A'
  }
];

const numberRegex = /[0-9]{6}/;

const res = Object.values(myArray.reduce((acc, curr) => {
  const { group, message } = curr;
  const isPhoneVerified = numberRegex.test(message);

  if (!acc[group] && isPhoneVerified) {
    acc[group] = { group: group, verified: 1, unverified: 0 };
  } else if (!acc[group] && !isPhoneVerified) {
    acc[group] = { group: group, verified: 0, unverified: 1 };
  } else if (acc[group] && isPhoneVerified) {
    acc[group].verified += 1;
  } else if (acc[group] && !isPhoneVerified) {
    acc[group].unverified += 1;
  }

  return acc;

}, {}));

console.log(res);

我忍不住稍微重构一下你的代码。就是说。我做了什么:

  • 用数组 ([]) 启动累加器
  • 如果尚未初始化,则将组推送到数组
  • 增加 verifiedunverified 取决于你的测试是否失败

const myArray = [
  { group: "groupA", message: "Text without a number", sl: "1A" },
  { group: "groupA", message: "Text with a number WO5467829", sl: "1A" },
  { group: "groupB", message: "Text without a number", sl: "1A" },
  { group: "groupA", message: "Text with a number WO5467829", sl: "1A" },
  { group: "groupB", message: "Text with a number WO5467829", sl: "1A" },
  { group: "groupC", message: "Text without a number", sl: "1B" },
  { group: "groupD", message: "Text with a number Tick0127866", sl: "1B" },
  { group: "groupC", message: "Text without a number", sl: "1A" }
];

output = myArray.reduce((acc, line) => {
  if( acc.findIndex(e => e.group === line.group) === -1 ) {
   acc.push({
      group: line.group,
      verified: 0,
      unverified: 0
    });
  }
  
  let group = acc.find(e => e.group === line.group);

  if( line.message.match(/\d{6,}/) )
   group.verified++;
  else
   group.unverified++;

  return acc;
}, []);

console.log(output);