# Find Average Marks in an Array

Opeyemi AbdulRasheed used Ask the Experts™
on
Hello Experts!

I already got help on how to calculate Total and Average per Student. Now, I want to find Average Marks per SUBJECT as in the following :

SN       Name                     Eng           Maths         No_of_Subjects    Total      Avg
1          Stu1                        40             45                2                             85          42.5
2          Stu2                        50             55                2                             105        52.5
Subject Avg.          45              50

This is the code I'm currently using:
class Student
{
public \$ID;
public \$Name;
public \$Subjects = array();

// Functions to get Total and Average marks per student
public function getTotalMarks()
{
\$total = 0;
foreach(\$this->Subjects as \$subject => \$marks)
{
\$total += \$marks;
}
return \$total;
}

public function getAverageMarks()
{
if(!count(\$this->Subjects)) { return 0; }
return round(\$this->getTotalMarks() / count(\$this->Subjects), 1);
}
}

class ClassName
{
public \$ID;
public \$Name;
public \$Students = array();
public \$SubjectList = array();
}

Thank you so much
Comment
Watch Question

Do more with

EXPERT OFFICE® is a registered trademark of EXPERTS EXCHANGE®
Consultant
Commented:
I'm guessing you want the averages per each class, so you would adjust the definition of the ClassName. It would looks something like this:

class ClassName
{
public \$ID;
public \$Name;
public \$Students = array();
public \$SubjectList = array();

public function getSubjectAverages()
{
\$results = array();
foreach(\$this->SubjectList as \$subjectName)
{
\$results[\$subjectName] = \$this->getSubjectAverage(\$subjectName);
}
return \$results;
}

// Get the average marks of all students for one subject
public function getSubjectAverage(\$subjectName)
{
\$subjectTotalMarks = 0;
\$subjectStudentsWithMarks = 0;

foreach\$(this->Students as \$student)
{
if(isset(\$student->Subjects[\$subjectName]))
{
\$subjectStudentsWithMarks++;
\$subjectTotalMarks += \$student->Subjects[\$subjectName];
}
}

if(\$subjectStudentsWithMarks == 0) { return 0; }
return \$subjectTotalMarks / \$subjectStudentsWithMarks;
}
}

And you would call \$classObjectHere->getSubjectAverages() to get an array that looked like:

[Eng] = 45
[Maths] = 50

Commented:

I tried it like this but nothing happend:

foreach(\$Class->SubjectList as \$subject)
{
\$pdf->Cell(10, 5, \$subjectName->getSubjectAverage(), 1, 0, 'C');
}
Consultant

Commented:
\$Class->getSubjectAverage(\$subjectName)

Commented:
Consultant

Commented:
I noticed I have a typo in my code:
foreach\$(this->Students as \$student)

should be:
foreach(\$this->Students as \$student)

If you didn't fix that already, that could be the issue. If you DID fix it, then try logging the two variables out somewhere:

...
file_put_contents("/path/to/a/log.file", "{\$subjectTotalMarks} / {\$subjectStudentsWithMarks}");
if(\$subjectStudentsWithMarks == 0) { return 0; }
return \$subjectTotalMarks / \$subjectStudentsWithMarks;

...and then check that log file to see which value is 0.

Commented:
I already fixed that. The log file shows that both variables are 0

0 / 0
Consultant

Commented:
Can you show the actual code you're using for that function?

Commented:
Everything:
<?php

require('../assets/library/fpdf.php');
require('../includes/connection.php');
error_reporting(0);
// ================== CLASS DEFINITIONS ==================
class Student
{
public \$ID;
public \$Name;
public \$Subjects = array();

// Functions to get Total and Average marks per student
public function getTotalMarks()
{
\$total = 0;
foreach(\$this->Subjects as \$subject => \$marks)
{
\$total += \$marks;
}
return \$total;
}

public function getAverageMarks()
{
if(!count(\$this->Subjects)) { return 0; }
return round(\$this->getTotalMarks() / count(\$this->Subjects), 1);
}
}

class ClassName
{
public \$ID;
public \$Name;
public \$Students = array();
public \$SubjectList = array();

public function getSubjectAverages()
{
\$results = array();
foreach(\$this->SubjectList as \$subjectName)
{
\$results[\$subjectName] = \$this->getSubjectAverage(\$subjectName);
}
return \$results;
}

// Get the average marks of all students for one subject
public function getSubjectAverage(\$subjectName)
{
\$subjectTotalMarks = 0;
\$subjectStudentsWithMarks = 0;

foreach(\$this->Students as \$student)
{
if(isset(\$student->Subjects[\$subjectName]))
{
\$subjectStudentsWithMarks++;
\$subjectTotalMarks += \$student->Subjects[\$subjectName];
}
}
file_put_contents("../assets/log.file", "{\$subjectTotalMarks} / {\$subjectStudentsWithMarks}");
if(\$subjectStudentsWithMarks == 0) { return 0; }
return \$subjectTotalMarks / \$subjectStudentsWithMarks;
}
}

\$session = \$_POST['session'];
\$term = \$_POST['term'];
\$class_name = \$_POST['class_name'];

// ================== QUERY AND ORGANIZE DATA INTO CLASS OBJECTS ==================
// Our top-level data array
\$classes = array();

// Query the data and organize it into objects
\$rs = \$conn->query("SELECT Student_ID, Student_Name, Class_Name, Subject_Code, Total FROM view_subjects_enrollment WHERE Session = '\$session' AND Term = '\$term' AND Class_Name = '\$class_name' ORDER BY Subject_Code");
while(\$row = \$rs->fetch_assoc())
{
\$id      = \$row["Student_ID"];
\$name    = \$row["Student_Name"];
\$class   = \$row["Class_Name"];
\$subject = \$row["Subject_Code"];
\$marks   = \$row["Total"];

// Initialize new Class
if(!isset(\$classes[\$class]))
{
\$classes[\$class] = new ClassName();
\$classes[\$class]->Name = \$class;
}

// Record the subject for the class
\$classes[\$class]->SubjectList[\$subject] = \$subject;

// Initialize student
if(!isset(\$classes[\$class]->Students[\$name]))
{
\$classes[\$class]->Students[\$name] = new Student();
\$classes[\$class]->Students[\$name]->ID = \$id;
\$classes[\$class]->Students[\$name]->Name = \$name;
}

\$classes[\$class]->Students[\$name]->Subjects[\$subject] = \$marks;
}

class PDF extends FPDF
{

include ('../includes/connection.php');

\$term = \$_POST['term'];
\$session = \$_POST['session'];

// Logo
\$this->Image('../assets/img/logo.png',10,5,20);

// Title
\$sql = "SELECT * FROM tbl_school WHERE Status = 1";
\$result = \$conn->query(\$sql);

while(\$row = \$result->fetch_assoc()) {
\$this->SetFont('Arial','B',14);
\$this->Cell(277, 5, \$row['Sch_Name'], 0, 1, 'C');
\$this->SetFont('Arial','',10);
\$this->Cell(277, 5, \$row['Sch_Address'], 0, 1, 'C');
}
\$this->SetFont('Arial','B',12);
\$this->Cell(277, 10, 'BROAD SHEET', 0, 1, 'C');

}

// Page footer
function Footer()
{
\$currentDate = date("d-m-Y");
// Position at 1.5 cm from bottom
\$this->SetY(-15);
\$this->SetFont('Arial','B',8);
// Page number
\$this->Cell(92,5,'Page '.\$this->PageNo().'/{nb}', 'T', 0, 'C');
\$this->Cell(92,5,'Printed @ '.\$currentDate, 'T', 1, 'R');
}
}

// Instanciation of inherited class
\$pdf = new PDF('L', 'mm', 'A4');
\$pdf->AliasNbPages();

\$pdf->SetFont('Arial','B',9);
\$pdf->Cell(92, 5, 'CLASS: '.\$class_name, 'B', 0, 'C');
\$pdf->Cell(92, 5, 'TERM: '.\$term, 'B', 0, 'C');
\$pdf->Cell(92, 5, 'SESSION: '.\$session, 'B', 1, 'C');

// ================== BUILD OUTPUT TABLE ==================

\$pdf->SetFont('Arial','B',8);
// Now loop through our data
\$cnt = 1;
foreach(\$classes as \$Class)
{
// Build table - column headers
\$pdf->Cell(10, 5, 'SN', 1, 0, 'C');
\$pdf->Cell(20, 5, 'ADM. NO', 1, 0, 'C');
\$pdf->Cell(60, 5, 'NAME', 1, 0, 'C');
foreach(\$Class->SubjectList as \$subject)
{
\$pdf->Cell(10, 5, \$subject, 1, 0, 'C');
}

\$pdf->SetFont('Arial','B',6);
\$pdf->Cell(15, 5, 'NO OF SUB.', 1, 0, 'C');

\$pdf->SetFont('Arial','B',8);
\$pdf->Cell(15, 5, 'TOTAL', 1, 0, 'C');
\$pdf->Cell(15, 5, 'AVG', 1, 1, 'C');

\$pdf->SetFont('Arial','',8);
// Loop through students and populate the table
foreach(\$Class->Students as \$Student)
{
\$pdf->Cell(10, 5, \$cnt++, 1, 0, 'C');
\$pdf->Cell(20, 5, \$Student->ID, 1, 0, 'L');
\$pdf->Cell(60, 5, \$Student->Name, 1, 0, 'L');

foreach(\$Class->SubjectList as \$subject)
{
// Display the marks if the student has them for that subject, otherwise display a blank string
\$pdf->Cell(10, 5, (isset(\$Student->Subjects[\$subject]) ? \$Student->Subjects[\$subject] : ""), 1, 0, 'C');

}

\$pdf->Cell(15, 5, count(\$Student->Subjects), 1, 0, 'C');
\$pdf->Cell(15, 5, \$Student->getTotalMarks(), 1, 0, 'C');
\$pdf->Cell(15, 5, \$Student->getAverageMarks(), 1, 1, 'C');

}
\$pdf->Cell(10, 5, '', 1, 0, 'C');
\$pdf->Cell(20, 5, '', 1, 0, 'C');
\$pdf->Cell(60, 5, 'Subject Average', 1, 0, 'C');

foreach(\$Class->SubjectList as \$subject)
{
\$pdf->Cell(10, 5, \$Class->getSubjectAverage(\$subjectName), 1, 0, 'C');
}
\$pdf->Cell(15, 5, '', 1, 0, 'C');
\$pdf->Cell(15, 5, '', 1, 0, 'C');
\$pdf->Cell(15, 5, '', 1, 0, 'C');

}

?>
Consultant

Commented:
Ah.

foreach(\$Class->SubjectList as \$subject)
{
\$pdf->Cell(10, 5, \$Class->getSubjectAverage(\$subjectName), 1, 0, 'C');
}

Those variables have to match.

Commented:
You're such an excellent dev. Million thanks. It's working

Do more with