3
\$\begingroup\$

I'm after a collection of opinions regarding cohesion and coupling with my application to improve OO programming.

Control Class - Populates test data and calls main menu

import java.util.HashSet;
import java.util.Set;


public class Control {

public void run() {
    // Populate Test Data
    Student jane = new Student("jane");
    Student alex = new Student("alex");
    Student mike = new Student("mike");
    Student james = new Student("james");
    Student julia = new Student("julia");

    Set<Student> students = new HashSet<Student>();
    students.add(jane);
    students.add(alex);
    students.add(mike);
    students.add(james);
    students.add(julia);

    Module ufce1 = new Module("UFCE1", "Java");
    Module ufce2 = new Module("UFCE2", "Software Design");
    Module ufce3 = new Module("UFCE3", "C#");
    Module ufce4 = new Module("UFCE4", "Client Server");
    Module ufce5 = new Module("UFCE5", "Data Structures");

    Set<Module> modules = new HashSet<Module>();
    modules.add(ufce5);
    modules.add(ufce4);
    modules.add(ufce3);
    modules.add(ufce2);
    modules.add(ufce1);

    jane.addModule(ufce1);
    jane.addModule(ufce3);
    alex.addModule(ufce1);
    alex.addModule(ufce2);

    ufce1.addStudent(jane);
    ufce3.addStudent(jane);
    ufce1.addStudent(alex);
    ufce2.addStudent(alex);

    // Call main menu 
    Menu menu = new Menu();
    menu.mainMenu(students, modules);
}
}

Menu Class - displays menu for the user and calls either StudentManager or ModuleManager depending on selection made

import java.util.InputMismatchException;
import java.util.Scanner;
import java.util.Set;


public class Menu{

public void mainMenu(Set<Student> students, Set<Module> modules) {
    System.out.println("Welcome to Student Record System!");

    while (true) {
        System.out.println("\n\nSelect an option:");
        System.out.println(
                "1 List all student names"
                + "\n2 List all module details"
                + "\n3 List all students on a module"
                + "\n4 List all modules attached to a student"
                + "\n5 Attach a valid student to a valid module"
                + "\n6 Exit\n");

        Scanner scan = new Scanner(System.in);

        StudentManager studentManager = new StudentManager();
        ModuleManager moduleManager = new ModuleManager(); 

        try {
            int selection = scan.nextInt();
            switch (selection) {
                case 1:
                    studentManager.listStudents(students); 
                    break;
                case 2:
                    moduleManager.listModules(modules);
                    break;
                case 3:
                    studentManager.studentModuleSearch(students, modules);
                    break;
                case 4:
                    moduleManager.SearchModulesWithEnrolledStudents(modules, students);
                    break;
                case 5:
                    studentManager.enrolStudentToModule(students, modules);
                    break;
                case 6:
                    exitRoutine();
                    break;
                default:
                    System.out.println("Invalid selected made. You must enter a number between 1 and 6.");
            }

        } catch (InputMismatchException e) {
            System.out.println("Only numeric values are accepted here.");
        } 
        catch (Exception e) {
            System.out.println("Invalid input.");
        }
    }
}

public void exitRoutine() {
    System.out.println("Goodbye!");
    System.exit(0);
}

}

StudentModule Class - performs methods relating to students

import java.util.Scanner;
import java.util.Set;

public class StudentManager {

// List all students 
public void listStudents(Set<Student> students) {
    for (Student student : students) {
        System.out.printf("%s ", student);
    }
}

// Set up scanner to allow for searching of students 
public String readStudentName() {
    System.out.print("Search for a student: ");
    final Scanner scan = new Scanner(System.in);   
    final String readStudent = scan.next().trim();
    return readStudent;
}

// Search students and return all modules they are enrolled on to 
public void studentModuleSearch(Set<Student> students, Set<Module> modules) {
    final String readStudent = readStudentName();
    final Student student = searchStudent(readStudent, students);
    if (student == null) {
        printNoStudentFound(readStudent);
        return;
    }
    for (Module module : modules) {
        if (module.getStudents().contains(student)) {
            System.out.printf("%s ", module);
        }
    }
}

// Search for match between searched string and module name
public Student searchStudent(final String searchStudent, final Set<Student> students) {
    for (final Student student : students) {
        final String studentName = student.getName();
        if (searchStudent.equalsIgnoreCase(studentName)) {
            return student;
        }
    }
    return null;
}

// Print if no modules are found under that name
private void printNoStudentFound(String searchModule) {
    System.out.println("No student found with name: " + searchModule);
}

// enrol a student onto a module by searching for the student and module prior to enrolling them
public void enrolStudentToModule(Set<Student> students, Set<Module> modules) {
    final String readStudent = readStudentName();
    final Student student = searchStudent(readStudent, students);
    if (student == null) {
        printNoStudentFound(readStudent);
        return;
    }
    ModuleManager moduleManager = new ModuleManager();
    final String searchModule = moduleManager.readModuleName();
    final Module module = moduleManager.searchModule(searchModule, modules);
    if (module == null) {
        moduleManager.printNoModuleFound(searchModule);
        return;
    }

    if (module.getStudents().contains(student)) {
        System.out.println("\n" + student + " is already enrolled on to " + module);
    } else {
        student.addModule(module);
        module.addStudent(student);
        System.out.println("\n" + student + " has been successfully enrolled on to " + module);
    }
}
}

ModuleManager Class - Performs methods relating to modules

import java.util.Scanner;
import java.util.Set;


public class ModuleManager {

// List all modules 
public void listModules(Set<Module> modules) {
    for (Module module : modules) {
        System.out.printf("%s ", module);
    }
}

// Set up scanner to read module names 
public String readModuleName() {
    System.out.print("Search module code: ");
    final Scanner scan = new Scanner(System.in);
    final String readModule = scan.next().trim();
    return readModule;
}

// Search modules and return all students enrolled on it 
public void SearchModulesWithEnrolledStudents(Set<Module> modules, Set<Student> students) {
    final String searchModule = readModuleName();
    final Module module = searchModule(searchModule, modules);
    if (module == null) {
        printNoModuleFound(searchModule);
        return;
    }
    for (Student student : students) {
        if (student.getModules().contains(module)) {
            System.out.printf("%s ", student);
        }
    }
}

// Search for match between searched string and module name
public Module searchModule(final String searchedModuleName, final Set<Module> modules) {
    for (final Module module : modules) {
        final String moduleName = module.getName();
        if (searchedModuleName.equalsIgnoreCase(moduleName)) {
            return module;
        }
    }
    return null;
}

// Print if no modules are found under that name
public void printNoModuleFound(String searchModule) {
    System.out.println("No module found with name: " + searchModule);
}
}

Student Class - Create new Student objects

import java.util.HashSet;
import java.util.Set;

public class Student {

private String name;
private Set<Module> modules = new HashSet<Module>();

public Student(String name) {
    this.name = name;
}

public String getName() {
    return name;
}

public Set<Module> getModules() {
    return modules;
}

// enrol students from test data onto a module 
public void addModule(Module module) {
    modules.add(module);
}

@Override
public String toString() {
    return name;
}
}

Module Class - Creates new Module objects

import java.util.HashSet;
import java.util.Set;

public class Module {

private String name, description;
private Set<Student> students = new HashSet<Student>();

public Module(String name, String description) {
    this.name = name;
    this.description = description;
}

public String getName() {
    return name;
}

public Set<Student> getStudents() {
    return students;
}

// attach modules from test data to a student 
public void addStudent(Student student) {
    students.add(student);
}


@Override
public String toString() {
    return name + " " + description;
}
}
\$\endgroup\$
0

2 Answers 2

1
\$\begingroup\$

What if I need to process student/module registrations using a text file instead of asking interactively? I would decouple I/O from the controller logic (StudentManager, ModuleManager, etc).

\$\endgroup\$
1
  • \$\begingroup\$ Thanks for the response. I'm not worried about taking inputs from text files at this stage. I'm merely looking for opinions relating to the remainder of the code. Relevant methods in classes? loose coupling and tight coupling? Perhaps the enrolStudentToModule method in StudentManager class should be in a separate method? Looking for responses along that line. \$\endgroup\$ Commented Dec 7, 2011 at 7:59
1
\$\begingroup\$

Just two quick pointers:

public void SearchModulesWithEnrolledStudents(Set<Module> modules, Set<Student> students)

should be camel cased

public void searchModulesWithEnrolledStudents(Set<Module> modules, Set<Student> students)

and a quick rewrite of

public Module searchModule(final String searchedModuleName, final Set<Module> modules) {
    for (final Module module : modules) {
        final String moduleName = module.getName();
        if (moduleName.equalsIgnoreCase(searchedModuleName)) {
            return module;
        }
    }
    return null;
}

so it won't crash on a call with:

foo.searchModule(null, modules)
\$\endgroup\$