Skip to main content
deleted 71 characters in body
Source Link

Functions should do one thing, do it completely, and do it well.

When a function is this long, it makes it Long functions are difficult to reason about.

I'm not including them here, rather I'm assuming the presence of String getSubjectCode() and Pupil getPupilInformation() methods, each containing the current code embeddedcurrently in other functionalitythe mega-function.

School.getSubjects() should return a List<Subject> (or Collection). (Or at least a properly-typed array; nothing with Objects.)

In the loopThere's a lot of code in block that loops over the school's subjects, you have a large bodymost of code insidewhich is the block for when the subject is found.

Better toIn cases like that, might as well do thea negative test and continue in this case, slightly "flattening" the loop's guts. (Code turned on its side is not a graph of how awesome it is ;)

That said, this functionality is available in a contains etc. and loopingmethod--looping in the mainline code isn't necessary. See next.

As per the above, the functionality for findingDeciding if a school has a specificgiven subject should be moved into the School class, for example:

This workAll the above turns the mainline code into the following:

Functions should do one thing, do it completely, and do it well.

When a function is this long, it makes it difficult to reason about.

I'm not including them here, rather I'm assuming the presence of String getSubjectCode() and Pupil getPupilInformation() methods, each containing the current code embedded in other functionality.

School.getSubjects() should return a List<Subject> (or Collection).

In the loop over the school's subjects, you have a large body of code inside the block for when the subject is found.

Better to do the negative test and continue in this case. That said, this functionality is available in a contains etc. and looping in the mainline code isn't necessary. See next.

As per the above, the functionality for finding if a school has a specific subject should be moved into the School class, for example:

This work turns the mainline code into the following:

Functions should do one thing, do it completely, and do it well. Long functions are difficult to reason about.

I'm assuming the presence of String getSubjectCode() and Pupil getPupilInformation() methods, each containing the code currently in the mega-function.

School.getSubjects() should return a List<Subject> (or Collection). (Or at least a properly-typed array; nothing with Objects.)

There's a lot of code in block that loops over the school's subjects, most of which is the block for when the subject is found.

In cases like that, might as well do a negative test and continue, slightly "flattening" the loop's guts. (Code turned on its side is not a graph of how awesome it is ;)

That said, this functionality is available in a contains method--looping in the mainline code isn't necessary. See next.

Deciding if a school has a given subject should be moved into the School class, for example:

All the above turns the mainline code into the following:

Source Link

The function is very long.

Functions should do one thing, do it completely, and do it well.

When a function is this long, it makes it difficult to reason about.

Move the subject and pupil data entry into separate functions to isolate the functionality, and streamline the mainline code.

I'm not including them here, rather I'm assuming the presence of String getSubjectCode() and Pupil getPupilInformation() methods, each containing the current code embedded in other functionality.

Naming conventions

Minor, but you call an instance of the Pupil class Pupil, which is confusing at best, misleading at worst. Non-static-final variables should always begin with lowercase letters.

Use typed collections

School.getSubjects() should return a List<Subject> (or Collection).

Reduce the amount of code in conditionals

In the loop over the school's subjects, you have a large body of code inside the block for when the subject is found.

In order to understand what happens if the subject isn't found, I have to scroll down to the end of that block, make sure I'm reading the indentation correctly (assuming the indentation is correct), only to find there's nothing there.

Better to do the negative test and continue in this case. That said, this functionality is available in a contains etc. and looping in the mainline code isn't necessary. See next.

Localize functionality

As per the above, the functionality for finding if a school has a specific subject should be moved into the School class, for example:

public class School {
    // ... existing functionality elided ...
    
    /** Returns subject with given code, or null if not found. */
    public Subject findSubjectByCode(String code) {
        for (Subject s : subjects) {
            if (s.getCode().equals(code)) {
                return s;
            }
        }
        return null;
    }
}

The refactored mainline code

This work turns the mainline code into the following:

System.out.println("Adding a Pupil...");

String subjectCode = getSubjectCode();
Subject schoolSubject = school.findSubjectByCode(subjectCode);
if (schoolSubject == null) {
    System.out.printf("A Subject with code, %s, doesn't exist!%n", subjectCode);
    return;
}

Pupil pupil = getPupilInformation();
if (schoolSubject.addPupil(pupil)) {
    System.out.printf("%nPupil, %s, has been added to the %s Subject.%n", pupil.getName(), subj.getName());
} else {
    System.out.printf("Pupil #%s is already in the Subject!%n", pupil.getID());
}

IMO this is more communicative, cleaner, and easier to understand.