# Grade calculator for a project with four aspects

I have a program that will ask the user to input their grades for 4 different sections of a project, then tell them what their total mark is, what grade they got and how many marks away they were from the next grade. I managed to make a single loop for all inputs rather than having a loop for each individual one, but there are still quite a lot of if statements to determine what grade they got and how far away they were from the next one, and I can't figure out how to optimise it since I'm still very new to Java.

import java.util.Arrays;
import java.util.InputMismatchException;
import java.util.Scanner;

public static void main(String[] args) {
// TODO Auto-generated method stub
String[] words = new String[]{"Analysis", "Design", "Implementation", "Evaluation"};
int[] marks = new int[words.length];
for(int counter = 1; counter <= words.length; counter++) {
System.out.println("Enter your mark for the '" + words[counter - 1] + "' part of the project: ");
while(true) {
try {
if(marks[counter - 1] < 0 || marks[counter - 1] > 25) {
System.out.println("Please input a number between 0 and 25.");
continue;
}
break;
} catch(InputMismatchException e) {
}
}
}

int totalmark = Arrays.stream(marks).sum();
Integer marksaway = null;

if(totalmark < 2) {
marksaway = 2 - totalmark;
} else if(totalmark >= 2 && totalmark < 4) {
marksaway = 4 - totalmark;
} else if(totalmark >= 4 && totalmark < 13) {
marksaway = 13 - totalmark;
} else if(totalmark >= 13 && totalmark < 22) {
marksaway = 22 - totalmark;
} else if(totalmark >= 22 && totalmark < 31) {
marksaway = 31 - totalmark;
} else if(totalmark >= 31 && totalmark < 41) {
marksaway = 41 - totalmark;
} else if(totalmark >= 41 && totalmark < 54) {
marksaway = 54 - totalmark;
} else if(totalmark >= 54 && totalmark < 67) {
marksaway = 67 - totalmark;
} else if(totalmark >= 67 && totalmark < 80) {
marksaway = 80 - totalmark;
} else if(totalmark >= 80) {
}

System.out.println("Your total mark was " + totalmark + ".");
} else if(marksaway == 1) {
System.out.println("You were " + marksaway + " mark away from a Grade " + nextgrade + ".");
} else {
System.out.println("You were " + marksaway + " marks away from a Grade " + nextgrade + ".");
}
}
}


Because there are no holes you can simply have an array of "breakpoints".

int [] steps = new int[] { 2, 4, 13, 22, 31, 41, 54, 67, 80 };
int i;

for(i=0; i<steps.length && totalmark>=steps[i]; i++);
grade = i==0 ? "U" : ""+i;
if(i<steps.length) marksaway=steps[i]-totalmark;

• Would you mind giving me a fairly simple explanation as to how this works? – Gameskiller01 Dec 12 '18 at 15:18
• The loop loops over the array and breaks out if toolmark greater the current array-entry. I.e. totalmark=3. First loop, i is 0 and totalmark is greater than steps[0] -> continue -- Second loop, i is 1 and totalmark is not greater than steps[1] -> break out of the loop with i=1. Set grade to "1", marksaway to steps[1]-totalmark and nextgrade to "2" – Holger Dec 12 '18 at 16:01

I tidied up the first section for you a bit and then implemented the technique suggested by @Holger, all seems to work perfectly after running a few tests.

import java.util.Arrays;
import java.util.InputMismatchException;
import java.util.Scanner;

public class MarkCalculator {

public static void main(String[] args) {
// TODO Auto-generated method stub
String[] words = new String[]{"Analysis", "Design", "Implementation", "Evaluation"};
int[] steps = { 2, 4, 13, 22, 31, 41, 54, 67, 80 };
int[] marks = new int[4];

Scanner reader = new Scanner(System.in); // Keep instantiation of scanner outside of loop - once is enough

int totalmark = 0;
int inputMark = 0;
int marksaway = Integer.MIN_VALUE;

for(int counter = 0; counter<words.length; counter++) {
System.out.println("Enter your mark for the '" + words[counter] + "' part of the project: ");
try {
do {
if(inputMark < 0 || inputMark > 25)
System.out.println("Please input a number between 0 and 25.");
else
marks[counter] = inputMark;
} while(inputMark < 0 || inputMark > 25);
} catch(InputMismatchException e) {
counter--;
}
}

totalmark = Arrays.stream(marks).sum();

for(int i=0; i<steps.length && totalmark>=steps[i]; i++) {
grade = (i==0 ? "U" : ""+i);
if(i < steps.length) {
marksaway = steps[(i+1)]-totalmark;
}
}

System.out.println("Your total mark was " + totalmark + ".");