Home > Software engineering >  Compare itens of an object array
Compare itens of an object array

Time:09-14

This is my array of objects:

const cart = [
  { group: "group 1", qtd: 12, value: 65, term: 20 }, //index 0
  { group: "group 1", qtd: 10, value: 100, term: 20 }, //index 1
  { group: "group 1", qtd: 18, value: 40, term: 10 }, //index 2
  { group: "group 2", qtd: 5, value: 30, term: 25 }, //index 3
  { group: "group 2", qtd: 22, value: 10, term: 25 }, //index 4
  { group: "group 3", qtd: 6, value: 60, term: 12 } //index 5
];

And I need to do some treatments to get this output:

result = [
  { group: "group 1", value: 1780, term: 20 },
  { group: "group 1", value: 720, term: 10 },
  { group: "group 2", value: 370, term: 25 },
  { group: "group 3", value: 360, term: 12 }
];

If the group is equal and the term is equal too, I need to add the qtd and the value of the indexes that matches with this rule. In this exemple, index 0 and 1 matches with the rule, so I make (12 * 65) (10 * 100) = 1780 | index 3 and 4 matches too, so I make (5 * 30) (22 * 10) = 370. And if the terms doesn't match, I just sum like in the other cases and show separately, like in indexes 2 and 5.

First i was trying to get the distinct elements of this object and how much times and how many times did it repeat itself, so I use lodash for this:

const counts = _.countBy(cart, "group");

And the output:

{ 'group 1': 3, 'group 2': 2, 'group 3': 1 }

And from that logic I can't think of a solution

I already try I lot of logics but I can't get anywhere, I would be very grateful if someone could help me in this logic.

CodePudding user response:

Here's one way. Use array.reduce as an iterator, then create a sort of temporary ID to track according to your requirements - the id combines the group name and the term. So the iterator keeps a record of the objects like {"group 1_20" : { ...data} so you can easily find a matching set of values to add together the numbers. Finally, remove those temporary ID keys with Object.values()

const cart = [
  { group: "group 1", qtd: 12, value: 65, term: 20 }, //index 0
  { group: "group 1", qtd: 10, value: 100, term: 20 }, //index 1
  { group: "group 1", qtd: 18, value: 40, term: 10 }, //index 2
  { group: "group 2", qtd: 5, value: 30, term: 25 }, //index 3
  { group: "group 2", qtd: 22, value: 10, term: 25 }, //index 4
  { group: "group 3", qtd: 6, value: 60, term: 12 } //index 5
];

const result = Object.values(cart.reduce((b, a) => {
  let iden = a.group   "_"   a.term;
  if (b[iden]) {
    b[iden] = { ...b[iden],
      value: b[iden].value   (a.qtd * a.value)
    }
  } else {
    a.value = a.qtd * a.value;
    delete a.qtd;
    b[iden] = a;
  }
  return b;
}, {}))

console.log(result)

CodePudding user response:

You could group by the wanted keys and take an object for grouping. At result take the values of the object.

const
    cart = [{ group: "group 1", qtd: 12, value: 65, term: 20 }, { group: "group 1", qtd: 10, value: 100, term: 20 }, { group: "group 1", qtd: 18, value: 40, term: 10 }, { group: "group 2", qtd: 5, value: 30, term: 25 }, { group: "group 2", qtd: 22, value: 10, term: 25 }, { group: "group 3", qtd: 6, value: 60, term: 12 }],
    keys = ['group', 'term'],
    result = Object.values(cart.reduce((r, { qtd, value, ...o }) => {
        const key = keys.map(k => o[k]).join('|');
        r[key] ??= { ...o, value: 0 };
        r[key].value  = qtd * value;
        return r;
    }, {}));

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

CodePudding user response:

const cart = [
  { group: "group 1", qtd: 12, value: 65, term: 20 }, //index 0
  { group: "group 1", qtd: 10, value: 100, term: 20 }, //index 1
  { group: "group 1", qtd: 18, value: 40, term: 10 }, //index 2
  { group: "group 2", qtd: 5, value: 30, term: 25 }, //index 3
  { group: "group 2", qtd: 22, value: 10, term: 25 }, //index 4
  { group: "group 3", qtd: 6, value: 60, term: 12 } //index 5
];

const result = Object.values(cart.reduce((acc, el) => {
  const key = el.group   "_"   el.term;
  if (!acc[key]) acc[key] = {group: el.group, term: el.term, value: 0};
  acc[key].value  = el.qtd * el.value;
  return acc;
}, {}));

console.log(result);

  • Related