public void testAverageForNoScores() { Performance performance = new Performance(); assertEquals(0.0, performance.average()); } If you run this, oops! You get a NullPointerException. That can be solved by initializing the integer array of tests defined in Performance to an empty array: private int[] tests = {}; When rerunning the tests, you get a different exception: junit.framework.AssertionFailedError: expected:<0.0> but was:<NaN> NaN is a constant defined on both the java.lang.Float and java.lang.Double classes that means "Not a Number." If there are no scores, tests.length() returns 0, meaning you are dividing by zero in this line of code: return total / tests.length; When it works with integers, Java throws an ArithmeticException to indicate that you are dividing by zero. With floating-point numbers, you get NaN, which is a legitimate floating-point number. Fix the problem by checking the number of test scores as the very first thing in average. public double average() { if (tests.length == 0) return 0.0; int total = 0; for (int score: tests) total += score; return (double)total / tests.length; } NaN has some interesting characteristics. Any boolean comparisons against NaN always result in false, as these language tests demonstrate: assertFalse(Double.NaN > 0.0); assertFalse(Double.NaN < 1.0); assertFalse(Double.NaN == 1.0); You might want the average method to return NaN. But how would you write the test, since you cannot compare NaN to any other floating-point number? Java supplies the isNaN static method, defined on both Float and Double, for this purpose: public void testAverageForNoScores() { Performance performance = new Performance(); assertTrue(Double.isNaN(performance.average())); } |