java - 我的 add 方法是否做了太多工作?

标签 java

我是编程新手,我一直犯着让一个方法做太多工作的错误。我的助教给了我一些建议,我应该致力于使一个方法足够可重用,这样我就可以在另一个程序中使用它,而不必进行太多修改。这确实帮助我以更好的方式处理写作方法,但我担心我可能使我的“添加”方法变得过于丰富。我应该把它分开,还是在技术上做“一件事”,即使它很厚实?

这是我的主类(引用的类只是基本模板,除了 getter 和 setter 之外没有做任何特殊的事情,所以我不会费心将它们发布在这里):

 import java.util.ArrayList;
 import java.util.InputMismatchException;
 import java.util.Scanner;

 enum ClassStanding{FRESHMAN,SOPHOMORE,JUNIOR,SENIOR,UNKNOWN,MASTERS_STUDIES,PHD_STUDIES};
 enum Major{CS,CEG,EE,ISE,BME,ME,MET,UNKNOWN};
 enum StudentType{UNDERGRADUATE,GRADUATE,UNDECLARED};

public class Main {

/**
 * @param args the command line arguments
 */
public static void main(String[] args) {
    Scanner stdin = new Scanner(System.in);
    ArrayList<Student> studentList = new ArrayList<>();
    int counter;
    boolean continueInput;
    int contCounter;
    do {
    do {
    System.out.print("Please enter what you want to do-ADD, REMOVE, LIST, or SAVE: ");
    switch (stdin.next().toLowerCase()) {
        case "add": add(stdin, studentList); counter = 0; break;
        case "remove": counter = 0; break;
        case "list": counter = 0; break;
        case "save": counter = 0; break;
        default: System.out.println("Improper input, please enter only ADD, REMOVE, LIST, or SAVE."); counter = 1; 
    }
    } while (counter == 1);
    do {
    System.out.print("\nDo you want to continue? Yes or no: ");
    switch (stdin.next().toLowerCase()) {
        case "yes": contCounter = 0; continueInput = true; break;
        case "no": contCounter = 0; continueInput = false; break;
        default: contCounter = 1; continueInput = false; System.out.print("\nPlease only enter 'yes' or 'no'.");
    }
    } while (contCounter == 1);
    } while (continueInput);
} // end main method

public static void add(Scanner stdin, ArrayList<Student> studentList) { // this is the one
    String firstName;
    String lastName;
    String uid;
    StudentType studentType;
    ClassStanding studentClassStanding;
    Major major;
    double overallGPA;
    double majorGPA;
    String majorProfessor;
    boolean thesisOption;
    System.out.print("Please enter the student's first name: ");
    String tempName = stdin.next();
    firstName = checkName(tempName);
    System.out.print("Please enter the student's last name: ");
    tempName = stdin.next();
    lastName = checkName(tempName);
    System.out.println("Please enter the student's UID in the format 'U####' or 'U#####': ");
    String tempUID = stdin.next();
    uid = checkUID(tempUID).toUpperCase();
    int count;
    do {
        System.out.print("Please enter the student's status as UNDECLARED, UNDERGRADUATE, or GRADUATE: ");
    switch (stdin.next().toUpperCase()) {
        case "UNDECLARED":
            studentType = StudentType.UNDECLARED;
            studentClassStanding = setStudentClassStanding(studentType);
            count = 0;
            Student student = new Student(firstName, lastName,
                    uid, studentType, studentClassStanding);
            studentList.add(student);
            break;
        case "UNDERGRADUATE":
            studentType = StudentType.UNDERGRADUATE;
            major = setMajor();
            studentClassStanding = setStudentClassStanding(studentType);
            System.out.println("Enter the student's overall GPA below.");
            overallGPA = setGPA();
            System.out.println("Enter the student's major GPA below.");
            majorGPA = setGPA();
            count = 0;
            UnderGraduate underGraduate = new UnderGraduate(firstName, lastName, uid, studentType,
                    studentClassStanding, major, overallGPA, majorGPA);
            studentList.add(underGraduate);
            break;
        case "GRADUATE":
            studentType = StudentType.GRADUATE;
            studentClassStanding = setStudentClassStanding(studentType);
            majorProfessor = setMajorProfessor();
            thesisOption = setThesisOption();
            count = 0;
            Graduate graduate = new Graduate(firstName, lastName, uid, studentType,
                    studentClassStanding, majorProfessor, thesisOption);
            studentList.add(graduate);
            break;
        default:
            System.out.println("Please enter either Undeclared, Undergraduate, or Graduate only.");
            count = 1;
    }
    } while (count == 1);
}

public static String checkName(String tempName) {
    int a = 1;
    String name1;        
    Scanner scanner = new Scanner(System.in);
    do {
        name1 = tempName; // hold the value of firstName in name1
        for (int i = 0; i < tempName.length(); i++) { // loop to check input consists of letters (is a name)
            if (!Character.isLetter(tempName.charAt(i))) { // if non-letters detected, ensure this was intentional
                System.out.println("Please ensure you've entered the correct name. Re-enter the name or enter 'continue' to proceed: ");
                tempName = scanner.nextLine();
                if (tempName.equalsIgnoreCase("continue")) { // if user enters "continue", use original input
                    a = 0;
                    tempName = name1; // pass name1 value to firstName
                    break;
                } else {
                    a = 1; // continue prompting for firstName
                }
            } else { // accept input
                a = 0;
            }
        }
    } while (a == 1); // loop to ensure proper input
    return tempName;
} // end checkName method

public static String checkUID(String tempUID) {
    Scanner scan = new Scanner(System.in);
    int a;
    do {
        if (tempUID.charAt(0) == 'U' || tempUID.charAt(0) == 'u') {
            if (tempUID.length() == 6 || tempUID.length() == 5) {
                a = 0;
            } else {
                a = 1;
                System.out.print("Please ensure input is in the form of U#### or U#####. Please re-enter the UID: ");
                tempUID = scan.next();
            }
        } else {
                a = 1;
                System.out.print("Please ensure input is in the form of U#### or U#####. Please re-enter the UID: ");
                tempUID = scan.next();
        }
    } while (a == 1);
    return tempUID;
} // end checkUID method

public static ClassStanding setStudentClassStanding(StudentType studentType) {
    Scanner scan = new Scanner(System.in);
    int count;
    ClassStanding studentTempClassStanding = null;
    do {
        if (studentType == StudentType.UNDECLARED || studentType == StudentType.UNDERGRADUATE) {
        System.out.print("Please enter the student's class standing as either Freshman, Sophomore, Junior, Senior, or Unknown: ");
        switch (scan.next().toUpperCase()) {
            case "FRESHMAN":
                studentTempClassStanding = ClassStanding.FRESHMAN;
                count = 0;
                break;
            case "SOPHOMORE":
                studentTempClassStanding = ClassStanding.SOPHOMORE;
                count = 0;
                break;
            case "JUNIOR":
                studentTempClassStanding = ClassStanding.JUNIOR;
                count = 0;
                break;
            case "SENIOR":
                studentTempClassStanding = ClassStanding.SENIOR;
                count = 0;
                break;
            case "UNKNOWN":
                studentTempClassStanding = ClassStanding.UNKNOWN;
                count = 0;
                break;
            default:
                System.out.println("Please enter only Freshman, Sophomore, Junior, Senior, or Unknown.");
                count = 1;
        } 
        } else {
                System.out.print("Please enter the student's class standing as either 'Masters' for Masters Studies or 'PhD' for PhD Studies: ");
                switch (scan.next().toUpperCase()) {
                    case "MASTERS": studentTempClassStanding = ClassStanding.MASTERS_STUDIES; count = 0; break;
                    case "PHD": studentTempClassStanding = ClassStanding.PHD_STUDIES; count = 0; break;
                    default: System.out.println("Please enter only 'Masters' or 'PhD'.");
                count = 1;
                }
                }
    } while (count == 1);
    return studentTempClassStanding;
} // end setStudentClassStanding method

public static Major setMajor() {
    Major tempMaj = null;
    Scanner s = new Scanner(System.in);
    int c;
    do {
        System.out.print("Please enter the student's major as either CS, CEG, EE, ISE, BME, ME, MET, or Unknown: ");
        switch (s.next().toUpperCase()) {
            case "CS":
                tempMaj = Major.CS;
                c = 0;
                break;
            case "CEG":
                tempMaj = Major.CEG;
                c = 0;
                break;
            case "EE":
                tempMaj = Major.EE;
                c = 0;
                break;
            case "ISE":
                tempMaj = Major.ISE;
                c = 0;
                break;
            case "BME":
                tempMaj = Major.BME;
                c = 0;
                break;
            case "ME":
                tempMaj = Major.ME;
                c = 0;
                break;
            case "MET":
                tempMaj = Major.MET;
                c = 0;
                break;
            case "UNKOWN":
                tempMaj = Major.UNKNOWN;
                c = 0;
                break;
            default:
                System.out.println("Please enter only the specified values. ");
                c = 1;
        }
    } while (c == 1);
    return tempMaj;
} // end setMajor method

public static double setGPA() {
    Scanner s = new Scanner(System.in);
    double gpa;
    int a;
    do {
            try {
                System.out.print("Please enter the student's GPA: ");
                gpa = s.nextDouble();// read in the gpa
                if (gpa < 0.0 || gpa > 4.0) { // ensure the gpa is in the correct range
                    System.out.println("Invalid input, please enter a positive value between 0.0 and 4.0.");
                    a = 1;
                } else {
                    a = 0;
                }
            } catch (InputMismatchException ex) { //catch any exceptions, prompt for correct input
                a = 1;
                gpa = 0.0;
                System.out.println("Sorry, please enter a double value.");
                s.nextLine(); // skip the last input
            }
        } while (a == 1 || gpa < 0.0 || gpa > 4.0); //loop while gpa is negative or incorrect input is received
    return gpa;
} // end setGPA method

private static String setMajorProfessor() {
    Scanner s = new Scanner(System.in);
    String prof;
    System.out.print("Please enter the name of the major professor: ");
    String tempName = s.nextLine();
    prof = checkName(tempName);
    return prof;
} // end setMajorProfessor method

private static boolean setThesisOption() {
    Scanner s = new Scanner(System.in);
    boolean thesis = false;
    int a;
    do {
    System.out.print("Please enter 'yes' if a thesis will be written, otherwise enter 'no': ");
    switch (s.next().toUpperCase()) {
        case "YES": thesis = true; a = 0; break;
        case "NO": thesis = false; a = 0; break;
        default: System.out.println("Please enter only 'yes' or 'no'."); a = 1;
    }
    } while (a == 1);
    return thesis;
} // end setThesisOption method

}

这个项目的重点是为用户提供一个选项菜单(添加、列表、保存、排序、删除),允许他们在他们提供的数组列表上执行一系列操作(通过 add 函数)。显然我还没有完成,我也不是在为我的项目寻求帮助,我只是想知道我的“添加”方法是否太丰富了。我试图通过调用其他方法来完成其中的大量工作来尽可能地分解它,但我仍然觉得该方法可能工作量太大。但话又说回来,这可能没问题,我真的不知道 - 我还没有感觉到一个方法到底应该做多少事情。

最佳答案

是的,这确实做得太多了。

在软件设计中,人们引入了所谓的难闻GRASP模式设计模式,为讨论提供更多科学论据.

<小时/>

难闻的气味:也称为反模式。它们包括例如上帝类(一个做所有事情的类),在这里似乎非常适用。这些是您应该重构代码的警报。

<小时/>

GRASP 模式:这些或多或少是代码应该移动的方向。这里适用的两个是 Controller 和低耦合:将 I/O 和数据操作相互分开,并确保大多数方法不需要其他方法提供/存储的数据方法/类。

<小时/>

设计模式:这些是一组可以用来实现 GRASP 模式的模式。例如,您可以使用工厂来构建新实例,或者使用责任链将问题拆分为单独处理的小子问题。

<小时/>

一些最终的引用建议:

  • “两个或更多,使用for” - E. W. Dijkstra
  • “在大多数情况下,一个方法不应包含超过 15 行”- 我的一些老师

关于java - 我的 add 方法是否做了太多工作?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22902389/

相关文章:

java - 如何创建一个用于时间 sleep 的java实用程序类

java - 使用 PowerMock 避免 wait() 方法时出现 IllegalMonitorStateException

java - 如何解决错误 : java. sql.SQLException : No suitable driver in spring security?

java - 有没有办法用Java调用Selenium Webdriver中的nextElementSibling?

java - 有没有办法在 Mockito 运行的测试中 AutoWire WebApplicationContext

java - 如何从 Java 8 中的对象列表中获取两个属性的乘积

java - 异常捕获层次结构流程

java - WatchService:错过和未处理的事件

java - 无法从 '14.0.2' 确定 java 版本

java - 使用 java 从 HashSet 中查找连接的矩形