Média da matriz dentro de um objeto

Oct 12 2020

Tenho uma série de objetos que contém o nome e as marcas dos alunos. como abaixo

Preciso calcular as notas 'médias' de cada aluno e comparar as notas 'médias' para obter o melhor aluno. Estou tentando como abaixo, não estou conseguindo o que estou perdendo?

var Students = [
  {
    name: "Bob",
    marks: [78,80,89,90,68]
  },
  {
    name: "Alin",
    marks: [87,60,59,70,68]
  },
  {
    name: "bikash",
    marks: [82,60,79,60,80]
  }
];


for (let i = 0; i < Students.length; i++){
  var average = Students[i].reduce((total, next)=> total + next.marks) /2 
}

console.log(average)

Preciso ter notas médias de cada aluno para comparar os resultados de todos os alunos

Respostas

Doston Oct 12 2020 at 20:25

Se você estiver procurando por um loop tradicional:

const Students = [{
    name: 'Bob',
    marks: [78, 80, 89, 90, 68],
},
    {
        name: 'Alin',
        marks: [87, 60, 59, 70, 68],
    },
    {
        name: 'bikash',
        marks: [82, 60, 79, 60, 80],
    },
];

var average;
for (let i = 0; i < Students.length; i++){
    var marks = Students[i]["marks"];
    var total = 0;
    console.log(marks);
    for (var j = 0; j < marks.length; j++ ) {
        total += marks[j];
    }
    average = total / marks.length;

    // answer for question in the comment
    var msg = Students[i]["name"] + " has average mark: " + average;
    console.log(msg)

}

console.log(average)
3 Iosif Oct 12 2020 at 20:19

Talvez isto:

const students = [{
    name: 'Bob',
    marks: [78, 80, 89, 90, 68],
  },
  {
    name: 'Alin',
    marks: [87, 60, 59, 70, 68],
  },
  {
    name: 'bikash',
    marks: [82, 60, 79, 60, 80],
  },
];

const topStudent = students
  .map(student => ({
    ...student,
    averageMark: student.marks.reduce((a, b) => a + b, 0) / student.marks.length,
  }))
  .sort((a, b) => a.averageMark - b.averageMark)
  .pop();

console.log(topStudent);

1 Ifaruki Oct 12 2020 at 20:22

Aqui vamos nós. Ele retorna uma série de objetos com o nome e a pontuação média dos alunos.

Também é classificado da média mais alta para a mais baixa

let arr = [
    {
        name: "Bob",
        marks: [78,80,89,90,68]
    },

    {
        name: "Alin",
        marks: [87,60,59,70,68]
    },

    {
        name: "bikash",
        marks: [82,60,79,60,80]
    }
]

let averages = arr.map(({ marks, name }) => {
   let average = marks.reduce((a,v) => a + v) / marks.length
   return { name , average }
}).sort((a,b) => b.average - a.average);

let [{ name }] = averages;

console.log(averages)
console.log("top student: ", name);

JMP Oct 12 2020 at 20:23

Você precisa reducedo marksarray de cada um Student, não de um Studentobjeto, pois este não é um array.

nexté o próximo valor na matriz, não o próximo item em Students.

Finalmente, coloque a console.loglinha dentro do loop para obter todos os resultados impressos.

var Students = [
  {
    name: "Bob",
    marks: [78,80,89,90,68]
  },
  {
    name: "Alin",
    marks: [87,60,59,70,68]
  },
  {
    name: "bikash",
    marks: [82,60,79,60,80]
  }
];


for (let i = 0; i < Students.length; i++){
    var average = Students[i].marks.reduce((total, next)=> total + next) / Students[i].marks.length;
    console.log(average);
}

Greedo Oct 12 2020 at 20:25

Você também pode extraí-lo em uma função:

var Students = [
  {
    name: "Bob",
    marks: [78,80,89,90,68]
  },
  {
    name: "Alin",
    marks: [87,60,59,70,68]
  },
  {
    name: "bikash",
    marks: [82,60,79,60,80]
  }
];

// Student avarage
var averages = []
for (let i = 0; i < Students.length; i++){
  var avg = average(Students[i].marks);
  console.log(Students[i].name + ": " + avg)
  averages.push(avg)
}

// Total average
console.log("total average: " + average(averages))

function average(array) {
  return array.reduce((total, mark) => total + mark, 0) / array.length;
}

Nithish Oct 12 2020 at 20:29

Abaixo está uma das maneiras de encontrar o aluno com média máxima usando Array.reduce, Array.map.

var Students = [{name:"Alin",marks:[87,60,59,70,68]},{name:"Bob",marks:[78,80,89,90,68]},{name:"bikash",marks:[82,60,79,60,80]}];

const getTopStudent = (students) => {
//Find the avg of the current student
  const formattedStudents = students.map(student => ({...student, avg: student.marks.reduce((t, m) => t+m, 0)/student.marks.length}))
  return formattedStudents.reduce((res, student) => {
      //Check if the avg of the student in res object is less than the avg of the current student, then return current student.
    if((res.avg || 0) < student.avg){
      return {
        ...student
      }
    }
    return res;
  }, {})
}

console.log(getTopStudent(Students))
.as-console-wrapper {
  max-height: 100% !important;
}

Observação: no exemplo acima, não considerei se há mais de um aluno com o mesmo

Abaixo está o exemplo que retornará todos os alunos se a média for a mesma

var Students = [{name:"Alin",marks:[87,60,59,70,68]},{name:"Bob",marks:[78,80,89,90,68]},{name:"bikash",marks:[82,60,79,60,80]},{name:"Joey",marks:[78,80,84,90,73]}];

const getTopStudent = (students) => {
  const formattedStudents = students.map(student => ({ ...student,
    avg: student.marks.reduce((t, m) => t + m, 0) / student.marks.length
  }))
  const finalRes = formattedStudents.reduce((res, student) => {
  //if the res.avg is less than current student avg then update the res object with the new avg and the students
    if ((res.avg || 0) < student.avg) {
      return {
        avg: student.avg,
        students: [{ ...student }]
      }
    } else if ((res.avg || 0) === student.avg) {
    //If average of the current student is same as res.avg, then push the current student to the res.students
      res.students.push(student);
      return res;
    }
    return res;
  }, {});

  return finalRes.students;
}

//More than one student with max avg
console.log(getTopStudent(Students));

//One student with max avg
console.log(getTopStudent(Students.slice(0,3)));
.as-console-wrapper {
  max-height: 100% !important;
}