PTA-blog-3

                          PTA成绩计算系列题目分析

一、前言

  继菜单系列结束后,还没有缓过神,又迎来了成绩计算系列,真是一波未平一波又起。对于此次的三道题目来讲,起初,我的思路是菜单系列和成绩计算系列大差不差,可以仿造菜单系列的体系结构进行改造,但再尝试之后,略显麻烦,在听了课堂上罗老师讲解的一番思路之后茅塞顿开,利用ArrayList将各类数据进行储存,Comparator,Collections,Collator等进行成绩,课程名字的排序,利用正则表达式对控制台输入的数据进行分配(录入课程,录入成绩)。不论是平时测验还是平时作业,在题量和难度上对于我来说都是有点大和有点难的。但是在一次次完成作业,一次次完成测验中我不断的锻炼,编码能力也在不断提升。

二、设计与分析

7-1 课程成绩统计程序-1:

某高校课程从性质上分为:必修课、选修课,从考核方式上分为:考试、考察。

考试的总成绩由平时成绩、期末成绩分别乘以权重值得出,比如平时成绩权重0.3,期末成绩权重0.7,总成绩=平时成绩*0.3+期末成绩*0.7。

考察的总成绩直接等于期末成绩

必修课的考核方式必须为考试,选修课可以选择考试、考察任一考核方式。

1、输入:

包括课程、课程成绩两类信息。

课程信息包括:课程名称、课程性质、考核方式(可选,如果性质是必修课,考核方式可以没有)三个数据项。

课程信息格式:课程名称+英文空格+课程性质+英文空格+考核方式

课程性质输入项:必修、选修

考核方式输入选项:考试、考察

课程成绩信息包括:学号、姓名、课程名称、平时成绩(可选)、期末成绩

课程信息格式:学号+英文空格+姓名+英文空格+课程名称+英文空格+平时成绩+英文空格+期末成绩

以上信息的相关约束:

1)平时成绩和期末成绩的权重默认为0.3、0.7

2)成绩是整数,不包含小数部分,成绩的取值范围是【0,100】

3)学号由8位数字组成

4)姓名不超过10个字符

5)课程名称不超过10个字符

6)不特别输入班级信息,班级号是学号的前6位。

2、输出:

输出包含三个部分,包括学生所有课程总成绩的平均分、单门课程成绩平均分、单门课程总成绩平均分、班级所有课程总成绩平均分。

为避免误差,平均分的计算方法为累加所有符合条件的单个成绩,最后除以总数。

1)学生课程总成绩平均分按学号由低到高排序输出

格式:学号+英文空格+姓名+英文空格+总成绩平均分

如果某个学生没有任何成绩信息,输出:学号+英文空格+姓名+英文空格+"did not take any exams"

2)单门课程成绩平均分分为三个分值:平时成绩平均分(可选)、期末考试平均分、总成绩平均分,按课程名称的字符顺序输出

格式:课程名称+英文空格+平时成绩平均分+英文空格+期末考试平均分+英文空格+总成绩平均分

如果某门课程没有任何成绩信息,输出:课程名称+英文空格+"has no grades yet"

3)班级所有课程总成绩平均分按班级由低到高排序输出

格式:班级号+英文空格+总成绩平均分

如果某个班级没有任何成绩信息,输出:班级名称+英文空格+ "has no grades yet"

异常情况:

1)如果解析某个成绩信息时,课程名称不在已输入的课程列表中,输出:学号+英文空格+姓名+英文空格+":"+课程名称+英文空格+"does not exist"

2)如果解析某个成绩信息时,输入的成绩数量和课程的考核方式不匹配,输出:学号+英文空格+姓名+英文空格+": access mode mismatch"

以上两种情况如果同时出现,按第一种情况输出结果。

3)如果解析某个课程信息时,输入的课程性质和课程的考核方式不匹配,输出:课程名称+" : course type & access mode mismatch"

4)格式错误以及其他信息异常如成绩超出范围等,均按格式错误处理,输出"wrong format"

5)若出现重复的课程/成绩信息,只保留第一个课程信息,忽略后面输入的。

信息约束:

1)成绩平均分只取整数部分,小数部分丢弃

参考类图:


image.png

第一题代码如下,后续两道题目均是在此代码上进行修改与添加,后面会有具体说明。

import java.util.Scanner;
import java.util.ArrayList;
import java.util.Collections;
import java.text.Collator;
import java.util.Comparator;
import java.util.Locale;
public class Main {
        public static void main(String[] args) {
            Scanner input = new Scanner(System.in);
            String nextLine = input.nextLine();
            ParseInput handle=new ParseInput();
            while (!nextLine.equals("end")) {
                handle.parseInput(nextLine);//解析用户输入的每一行数据
                nextLine = input.nextLine();
            }
            handle.showStudents();
            handle.showCourses();
            handle.showClasses();
        }
}
class myClass implements Comparable<myClass>{
    private String ID;
    ArrayList<Student> listStudent=new ArrayList<>();
    void addStudent(Student stu){
        listStudent.add(stu);
    }
    public myClass(String ID) {
        this.ID = ID;
    }
    public String getID() {
        return ID;
    }
    @Override
    public int compareTo(myClass myclass){
        return ID.compareTo(myclass.getID());
    }
}
class Choose {
    Course course;
    Student student;
    Score score;

    public Course getCourse() {
        return course;
    }

    public Student getStudent() {
        return student;
    }

    public Choose(Course course, Student student, Score score) {
        this.course = course;
        this.student = student;
        this.score = score;
    }
}
abstract class Score{
    protected int Score2;//期末
    protected int totalScore;

    public int getTotalScore() {
        return totalScore;
    }

    public int getFinalScore() {
        return Score2;
    }

    Score(int finalScore){this.Score2=finalScore;}
}
class ksScore extends Score{
    private int Score1;//平时

    public int getUsualScore() {
        return Score1;
    }

    ksScore(int usualScore, int finalScore){
        super(finalScore);
        this.Score1=usualScore;
        this.totalScore=(int)(finalScore*0.7+usualScore*0.3);
    }
}
class kcScore extends Score{
    kcScore(int finalScore){
        super(finalScore);
        this.totalScore=finalScore;
    }
}
class Course implements Comparable<Course>{
    private String csName;
    private String csCharacter;
    private String csExamine;

    public Course(String csName, String csCharacter, String csExamine) {
        this.csName = csName;
        this.csCharacter = csCharacter;
        this.csExamine = csExamine;
    }

    public String getCsName() {
        return csName;
    }

    public String getCsCharacter() {
        return csCharacter;
    }

    public String getCsExamine() {
        return csExamine;
    }

    @Override
    public int compareTo(Course o) {
        Comparator<Object> compare = Collator.getInstance(Locale.CHINA);
        return compare.compare(csName,o.getCsName());
    }
}
class Student implements Comparable<Student>{
    private String stuNumber;
    private myClass myclass;
    private String stuName;

    public Student(String stuNumber, String stuName) {
        this.stuName=stuName;
        this.stuNumber=stuNumber;
    }

    public String getStNumber() {
        return stuNumber;
    }

    public String getStName() {
        return stuName;
    }

    @Override
    public int compareTo(Student student){
        return getStNumber().compareTo(student.getStNumber());
    }
}
class InputMatching {
    static String stuNumMatching = "[0-9]{8}";//8个0-9的数字
    static String stuNameMatching = "\\S{1,10}";//1到10个非空格(TAB)字符
    static String scoreMatching = "([1-9]?[0-9]|100)";
    static String courseNameMatching = "\\S{1,10}";//1到10个非空格(TAB)字符
    static String courseTypeMatching = "(选修|必修)";
    static String checkcourseTypeMatching = "(考试|考察)";
    //cousrInput用于定义课程信息模式(正则表达式)
    static String courseInput = courseNameMatching + " " + courseTypeMatching + " " + checkcourseTypeMatching;
    //scoreInput用于定义成绩信息模式(正则表达式)
    static String scoreInput = stuNumMatching + " " + stuNameMatching + " " + courseNameMatching + " " + scoreMatching;
    static String scoreInput1 = stuNumMatching + " " + stuNameMatching + " " + courseNameMatching + " " + scoreMatching + " "+scoreMatching;
    public static int matchingInput(String s) {
        if (matchingCourse(s)) {
            return 1;
        }
        if (matchingScore(s)) {
            return 2;
        }
        return 0;
    }

    private static boolean matchingCourse(String s) {
        return s.matches(courseInput);
    }

    private static boolean matchingScore(String s) {
        return (s.matches(scoreInput)||s.matches(scoreInput1));
    }
}
class ParseInput{
    ArrayList<Course> courseArrayList = new ArrayList<>();
    ArrayList<Student> studentArrayList = new ArrayList<>();
    ArrayList<Choose> chooseArrayList = new ArrayList<>();
    ArrayList<myClass> classArrayList = new ArrayList<>();

    public void parseInput(String nextLine) {
        String[] arraylist = nextLine.split(" ");
        switch (InputMatching.matchingInput(nextLine)){
            case 1:
                inputCourse(arraylist);
                break;
            case 2:
                inputScore(arraylist);
                break;
            case 0:
                System.out.println("wrong format");
                break;
        }
    }

    Course getCourse(String courseName){
        for (Course course : courseArrayList) {
            if (course.getCsName().equals(courseName))
                return course;
        }
        return null;
    }
    myClass getclass(String classId){
        for (myClass myClass : classArrayList) {
            if (myClass.getID().equals(classId))
                return myClass;
        }
        return null;
    }
    Student getStudent(String stuId){
        for (Student student : studentArrayList) {
            if (student.getStNumber().equals(stuId))
                return student;
        }
        return null;
    }

    private void inputScore(String[] a){
        myClass myclass;
        Student student;
        myclass=getclass(a[0].substring(0,6));
        if(myclass==null){
            myclass=new myClass(a[0].substring(0,6));
            classArrayList.add(myclass);
        }
        student=getStudent(a[0]);
        if(student==null){
            student=new Student(a[0], a[1]);
            studentArrayList.add(student);
            myclass.addStudent(student);
        }
        Course course=getCourse(a[2]);
        if(course==null){
            System.out.println(a[2]+" does not exist");
            return;
        }
        if(!checkGrade(a,course))
            return;
        Score score;
        if(a.length==4){
            score=new kcScore(Integer.parseInt(a[3]));
        }else {
            score=new ksScore(Integer.parseInt(a[3]),Integer.parseInt(a[4]));
        }
        if(existChooseCourse(student,course)) return;
        Choose chooseCourse = new Choose(course, student, score);
        chooseArrayList.add(chooseCourse);
    }

    public void inputCourse(String[] a){
        Course course = new Course(a[0],a[1],a[2]);
        if(!checkCourse(course))
            return;
        if(getCourse(a[0])==null){
            course=new Course(a[0], a[1], a[2]);
            courseArrayList.add(course);
        }
    }
    boolean checkCourse(Course course){
        if(course.getCsCharacter().equals("必修")&&course.getCsExamine().equals("考试"))
            return true;
        if(course.getCsCharacter().equals("选修")&&course.getCsExamine().equals("考试"))
            return true;
        if(course.getCsCharacter().equals("选修")&&course.getCsExamine().equals("考察"))
            return true;
        System.out.println(course.getCsName()+" : course type & access mode mismatch");
        return false;
    }
    boolean existChooseCourse(Student stu,Course course){
        for (Choose choose : chooseArrayList) {
            if (choose.getCourse().getCsName().equals(course.getCsName())) {
                if (choose.getStudent().getStName().equals(stu.getStName()))
                    return true;
            }
        }
        return false;
    }
    private boolean checkGrade(String[] items,Course course){
        String courseType=course.getCsExamine();
        if(courseType.equals("考试")&&items.length==5){
            return true;
        }
        if(courseType.equals("考察")&&items.length==4){
            return true;
        }
        System.out.println(items[0]+" "+items[1]+" : access mode mismatch");
        return false;
    }

    public static int getAvagScore1(ArrayList<Choose> courseSelects)//平时
    {
        int sum = 0;
        for(Choose cs : courseSelects)
        {
            sum +=((ksScore)(cs.score)).getUsualScore();
        }
        return sum/courseSelects.size();
    }
    public int getAvagScore2(ArrayList<Choose> courseSelects)//期末
    {
        int sum =0;
        for(Choose cs : courseSelects)
        {
            sum += cs.score.getFinalScore();
        }
        return sum/courseSelects.size();
    }
    public int getAvgTotalScore(ArrayList<Choose> listChooseCourse)
    {
        int sum =0;
        for(Choose cs : listChooseCourse)
        {
            sum +=cs.score.getTotalScore();
        }
        return sum/listChooseCourse.size();
    }

    public ArrayList<Choose> getStudentSelects(String stNumber) {
        ArrayList<Choose> stus = new ArrayList<>();
        for (Choose choose : chooseArrayList) {
            if (choose.student.getStNumber().equals(stNumber)) {
                stus.add(choose);
            }
        }
        if(stus.size()!=0)
            return stus;
        else return null;
    }

    public ArrayList<Choose> getCourseSelects(String courseName){
        ArrayList<Choose> courses = new ArrayList<>();
        for (Choose choose : chooseArrayList) {
            if (choose.course.getCsName().equals(courseName)) {
                courses.add(choose);
            }
        }
        if(courses.size()!=0)
            return courses;
        else return null;
    }

    public ArrayList<Choose> getClassSelects(String classID){
        ArrayList<Choose> classes = new ArrayList<>();
        for (Choose choose : chooseArrayList) {
            if (choose.student.getStNumber().substring(0, 6).equals(classID)) {
                classes.add(choose);
            }
        }
        if(classes.size()!=0)
            return classes;
        else return null;
    }
    public void showStudents() {
        Collections.sort(studentArrayList);
        for (Student student : studentArrayList) {
            ArrayList<Choose> stuCourseSelects = getStudentSelects(student.getStNumber());
            //从总选课表Choose中获取该生的选课记录集合
            if (stuCourseSelects != null) {
                System.out.println(student.getStNumber() + " " + student.getStName() + " " + getAvgTotalScore(stuCourseSelects));
            } else {
                System.out.println(student.getStNumber() + " " + student.getStName() + " " + "did not take any exams");
            }
        }
    }

    public void showCourses() {
        Collections.sort(courseArrayList);
        for (Course course : courseArrayList) {
            ArrayList<Choose> CourseSelects = getCourseSelects(course.getCsName());
            if (CourseSelects != null) {
                if (course.getCsExamine().equals("考试"))
                    System.out.println(course.getCsName() + " " + getAvagScore1(CourseSelects) + " " + getAvagScore2(CourseSelects) + " " + getAvgTotalScore(CourseSelects));
                if (course.getCsExamine().equals("考察"))
                    System.out.println(course.getCsName() + " " + getAvagScore2(CourseSelects) + " " + getAvgTotalScore(CourseSelects));
            } else {
                System.out.println(course.getCsName() + " has no grades yet");
            }
        }
    }

    public void showClasses() {
        Collections.sort(classArrayList);
        for (myClass myClass : classArrayList) {
            ArrayList<Choose> stuClassSelects = getClassSelects(myClass.getID());
            if (stuClassSelects != null) {
                System.out.println(myClass.getID() + " " + getAvgTotalScore(stuClassSelects));
            } else {
                System.out.println(myClass.getID() + " " + "has no grades yet");
            }
        }
    }
}

这道题的思路为先将输入的信息利用正则表达式进行匹配,区分为课程录入和成绩录入,创建4个集合

ArrayList<Course> courseArrayList = new ArrayList<>();
ArrayList<Student> studentArrayList = new ArrayList<>();
ArrayList<Choose> chooseArrayList = new ArrayList<>();
ArrayList<myClass> classArrayList = new ArrayList<>();

其中chooseArrayList作为总集合,其余三个集合分别储存班级,课程,学生信息。起初在测试运行时,总会爆出NullPointerException空指针的异常,即信息并没有成功录入到集合中里去,构造了如下方法得以解决。(在每添加一条信息后进行检查)

    boolean existChooseCourse(Student stu,Course course){
        for (Choose choose : chooseArrayList) {
            if (choose.getCourse().getCsName().equals(course.getCsName())) {
                if (choose.getStudent().getStName().equals(stu.getStName()))
                    return true;
            }
        }
        return false;
    }

类图:

 

接下来就是第二题:

7-3 课程成绩统计程序-2:

课程成绩统计程序-2在第一次的基础上增加了实验课,以下加粗字体显示为本次新增的内容。

某高校课程从性质上分为:必修课、选修课、实验课,从考核方式上分为:考试、考察、实验。

考试的总成绩由平时成绩、期末成绩分别乘以权重值得出,比如平时成绩权重0.3,期末成绩权重0.7,总成绩=平时成绩*0.3+期末成绩*0.7。

考察的总成绩直接等于期末成绩

实验的总成绩等于课程每次实验成绩的平均分

必修课的考核方式必须为考试,选修课可以选择考试、考察任一考核方式。实验课的成绩必须为实验。

1、输入:

包括课程、课程成绩两类信息。

课程信息包括:课程名称、课程性质、考核方式(可选,如果性质是必修课,考核方式可以没有)三个数据项。

课程信息格式:课程名称+英文空格+课程性质+英文空格+考核方式

课程性质输入项:必修、选修、实验

考核方式输入选项:考试、考察、实验

考试/考查课程成绩信息包括:学号、姓名、课程名称、平时成绩(可选)、期末成绩

考试/考查课程信息格式:学号+英文空格+姓名+英文空格+课程名称+英文空格+平时成绩+英文空格+期末成绩

实验课程成绩信息包括:学号、姓名、课程名称、实验次数、每次成绩

实验次数至少4次,不超过9次

实验课程信息格式:学号+英文空格+姓名+英文空格+课程名称+英文空格+实验次数+英文空格+第一次实验成绩+...+英文空格+最后一次实验成绩

以上信息的相关约束:

1)平时成绩和期末成绩的权重默认为0.3、0.7

2)成绩是整数,不包含小数部分,成绩的取值范围是【0,100】

3)学号由8位数字组成

4)姓名不超过10个字符

5)课程名称不超过10个字符

6)不特别输入班级信息,班级号是学号的前6位。

2、输出:

输出包含三个部分,包括学生所有课程总成绩的平均分、单门课程成绩平均分、单门课程总成绩平均分、班级所有课程总成绩平均分。

为避免误差,平均分的计算方法为累加所有符合条件的单个成绩,最后除以总数。

1)学生课程总成绩平均分按学号由低到高排序输出

格式:学号+英文空格+姓名+英文空格+总成绩平均分

如果某个学生没有任何成绩信息,输出:学号+英文空格+姓名+英文空格+"did not take any exams"

2)单门课程成绩平均分分为三个分值:平时成绩平均分(可选)、期末考试平均分、总成绩平均分,按课程名称的字符顺序输出

考试/考察课程成绩格式:课程名称+英文空格+平时成绩平均分+英文空格+期末考试平均分+英文空格+总成绩平均分

实验课成绩格式:课程名称+英文空格+总成绩平均分

如果某门课程没有任何成绩信息,输出:课程名称+英文空格+"has no grades yet"

3)班级所有课程总成绩平均分按班级由低到高排序输出

格式:班级号+英文空格+总成绩平均分

如果某个班级没有任何成绩信息,输出:班级名称+英文空格+ "has no grades yet"

异常情况:

1)如果解析某个成绩信息时,课程名称不在已输入的课程列表中,输出:学号+英文空格+姓名+英文空格+":"+课程名称+英文空格+"does not exist"

2)如果解析某个成绩信息时,输入的成绩数量和课程的考核方式不匹配,输出:学号+英文空格+姓名+英文空格+": access mode mismatch"

以上两种情况如果同时出现,按第一种情况输出结果。

3)如果解析某个课程信息时,输入的课程性质和课程的考核方式不匹配,输出:课程名称+" : course type & access mode mismatch"

4)格式错误以及其他信息异常如成绩超出范围等,均按格式错误处理,输出"wrong format"

5)若出现重复的课程/成绩信息,只保留第一个课程信息,忽略后面输入的。

信息约束:

1)成绩平均分只取整数部分,小数部分丢弃。

此题在第一次的基础上增加了实验课,实验课的考核方式与考核性质必须为实验,实验次数也有4-9的范围要求,为此,我在正则表达式上进行了改动,多加了如下的匹配规则

    static String scoreMatching1 = "([1-9]\\d{0,1}|0|100)( ([1-9]\\d{0,1}|0|100)){3,8}";
    static String courseTypeMatching = "(选修|必修|实验)";
    static String checkcourseTypeMatching = "(考试|考察|实验)";
    static String experimentNumber = "[4-9]";
    static String scoreInput3 = stuNumMatching + " " + stuNameMatching + " " + courseNameMatching + " " + experimentNumber +" "+scoreMatching1;

新增一个实验课程类,同样继承于成绩类。

class syScore extends Score{
    syScore(int [] a,int finalScore,int n){
        super(finalScore);
        int sum=0;
        for (int i = 0; i <n; i++) {
            sum+=a[i];
        }
        this.totalScore=sum/n;
    }
}

除此之外在ParseInput类中也要添加相应的关于实验课程的一些代码,例如:判断输入的实验成绩个数是否与实验次数匹配等

类图:

 接下来是第三题:

7-2 课程成绩统计程序-3:

课程成绩统计程序-3在第二次的基础上修改了计算总成绩的方式,

要求:修改类结构,将成绩类的继承关系改为组合关系,成绩信息由课程成绩类和分项成绩类组成,课程成绩类组合分项成绩类,分项成绩类由成绩分值和权重两个属性构成。

完成课程成绩统计程序-2、3两次程序后,比较继承和组合关系的区别。思考一下哪一种关系运用上更灵活,更能够适应变更。

题目最后的参考类图未做修改,大家根据要求自行调整,以下内容加粗字体显示的内容为本次新增的内容。

某高校课程从性质上分为:必修课、选修课、实验课,从考核方式上分为:考试、考察、实验。

考试的总成绩由平时成绩、期末成绩分别乘以权重值得出,比如平时成绩权重0.3,期末成绩权重0.7,总成绩=平时成绩*0.3+期末成绩*0.7。

考察的总成绩直接等于期末成绩

实验的总成绩等于课程每次实验成绩乘以权重后累加而得。

课程权重值在录入课程信息时输入。(注意:所有分项成绩的权重之和应当等于1)

必修课的考核方式必须为考试,选修课可以选择考试、考察任一考核方式。实验课的成绩必须为实验。

1、输入:

包括课程、课程成绩两类信息。

课程信息包括:课程名称、课程性质、考核方式、分项成绩数量、每个分项成绩的权重。

考试课信息格式:课程名称+英文空格+课程性质+英文空格+考核方式+英文空格+平时成绩的权重+英文空格+期末成绩的权重

考察课信息格式:课程名称+英文空格+课程性质+英文空格+考核方式

实验课程信息格式:课程名称+英文空格+课程性质+英文空格+考核方式+英文空格+分项成绩数量n+英文空格+分项成绩1的权重+英文空格+。。。+英文空格+分项成绩n的权重

实验次数至少4次,不超过9次

课程性质输入项:必修、选修、实验

考核方式输入选项:考试、考察、实验

考试/考查课程成绩信息包括:学号、姓名、课程名称、平时成绩(可选)、期末成绩

考试/考查课程成绩信息格式:学号+英文空格+姓名+英文空格+课程名称+英文空格+平时成绩+英文空格+期末成绩

实验课程成绩信息包括:学号、姓名、课程名称、每次成绩{在系列-2的基础上去掉了(实验次数),实验次数要和实验课程信息中输入的分项成绩数量保持一致}

实验课程信息格式:学号+英文空格+姓名+英文空格+课程名称+英文空格+第一次实验成绩+...+英文空格+最后一次实验成绩

以上信息的相关约束:

1)成绩是整数,不包含小数部分,成绩的取值范围是【0,100】

2)学号由8位数字组成

3)姓名不超过10个字符

4)课程名称不超过10个字符

5)不特别输入班级信息,班级号是学号的前6位。

2、输出:

输出包含三个部分,包括学生所有课程总成绩的平均分、单门课程总成绩平均分、班级所有课程总成绩平均分。

为避免四舍五入误差,

计算单个成绩时,分项成绩乘以权重后要保留小数位,计算总成绩时,累加所有分项成绩的权重分以后,再去掉小数位。

学生总成绩/整个班/课程平均分的计算方法为累加所有符合条件的单个成绩,最后除以总数。

1)学生课程总成绩平均分按学号由低到高排序输出

格式:学号+英文空格+姓名+英文空格+总成绩平均分

如果某个学生没有任何成绩信息,输出:学号+英文空格+姓名+英文空格+"did not take any exams"

2)单门课程成绩按课程名称的字符顺序输出

课程成绩输出格式:课程名称+英文空格+总成绩平均分

如果某门课程没有任何成绩信息,输出:课程名称+英文空格+"has no grades yet"

3)班级所有课程总成绩平均分按班级由低到高排序输出

格式:班级号+英文空格+总成绩平均分

如果某个班级没有任何成绩信息,输出:班级名称+英文空格+ "has no grades yet"

异常情况:

1)如果解析某个成绩信息时,课程名称不在已输入的课程列表中,输出:学号+英文空格+姓名+英文空格+":"+课程名称+英文空格+"does not exist"

2)如果解析某个成绩信息时,输入的成绩数量和课程的考核方式不匹配,输出:学号+英文空格+姓名+英文空格+": access mode mismatch"

以上两种情况如果同时出现,按第一种情况输出结果。

3)如果解析某个课程信息时,输入的课程性质和课程的考核方式不匹配,输出:课程名称+" : course type & access mode mismatch"

4)格式错误以及其他信息异常如成绩超出范围等,均按格式错误处理,输出"wrong format"

5)若出现重复的课程/成绩信息,只保留第一个课程信息,忽略后面输入的。

6)如果解析实验课程信息时,输入的分项成绩数量值和分项成绩权重的个数不匹配,输出:课程名称+" : number of scores does not match"

7)如果解析考试课、实验课时,分项成绩权重值的总和不等于1,输出:课程名称+" : weight value error"

信息约束:

1)成绩平均分只取整数部分,小数部分丢弃。

想要解决这道题首要重点是一定要仔细读题,一定要仔细读题,此题将期中期末考试的占比改为了控制台输入,输出格式改为只输出一个成绩,在正则表达式上也做出了相应的修改。

    static String decimalsRegex = "(\\d+\\.\\d+)( (\\d+\\.\\d+)){2,9}";
    static String decimals = "\\d+\\.\\d+";//小数

录入成绩也做出了相应修改,

class syScore extends Score{//实验
    syScore(int [] a,int finalScore,double [] b){
        super(finalScore);
        double sum= 0.0;
        for (int i = 0; i <a.length; i++) {
            for (int j = 0; j < b.length; j++) {
                sum+=(a[i]*b[i]);
            }
        }
        this.totalScore= (int)sum/a.length;
    }
}

将占比与成绩都存到数组里,再进行计算。其他内容只需要按照题目要求的来进行调整即可。

类图:

遗憾的是第三题最终没有取得满分,那一个测试点真的太难找了!

 

 

 三、采坑心得

  在我们编写较长代码,其中含有很多类很多方法的时候,我们会不知道如何使用相应的方法实现功能,因为再java中不再使用全局变量,所以很容易调用过来的是空的,这让我们经常出现错误。我们需要清楚的了解自己想要调用的东西是属于哪一个类中,定义该事物的时候是属于哪一个类中,这会方便我们将数据统合在一起,不会出错。我们只要在编写代码之前搞清楚了各个类之间的关系,不要囫囵吞枣,还没搞清楚之间的关系就开始下手敲代码,这会导致我们编写到途中发现自己的编写的程序前言不搭后语。所以每次我们动手前都需要想清楚各个类中需要编写什么方法,定义什么属性,以及各个类之间是什么关系,有什么关联,有什么方法是大家公共都会用到的。经过这三道成绩计算题目让我再一次理解到认真读题的重要性,也让我知道了以后做任何事一定要认真对待。重点吐槽一下第三道题,将精度作为一个陷阱我真的是醉了,编写完代码,给出的样例全都通过,信心满满的点击提交,迎面来的一片绿色真的很让人心痛。花了两三天时间坐在电脑前进行调整真的浪费时间,还有就是寻找测试点的过程,冗长乏味,又臭又长,自我感觉这个过程没有任何的意义,单纯的浪费时间!!!

四、改进建议

  在面对例如成绩管理系统这种需要较长时间去编写大量代码的题目中,我时常静不下心来去好好思考其中的奥秘,导致每次我花费较长时间也毫无收获,也是我经历少、能力不够的一种表现吧。并且在我最后编写完完整程序之后,发现我的程序有些地方并没有用最简洁的编程语言去表达实现功能。希望以后可以逐步提升自己的能力,用更加精简且让读者易于理解的编程语言去完成编程。重要的在一个学期的过程中,更改自己的编写格式是很重要的,我从起初的胡乱变成到现在可以基本按照大企那样规定的格式编程,但我仍然没有做到该注释的地方加以注释,希望以后我能改进这个地方。

五、总结

通过第三阶段的题目集训练,自己的编程能力相对与之前进步了一些,虽然与那些“大佬”同学他们相比,自己还差一大截,因此,自己还需在以后的空余时间自己坚持不懈的学习和实践,相信经过今后的学习和越来越多实践,自己对java这门编程语言也会越来越精通。在第三阶段(10-16周)中,还包括两次限时现场编程的题目集训练,一次期中测试,一次课堂测试,经过这两次的实践,我发现自身存在的一些问题:现场编程速度较慢,反映也比较慢,个别知识点不熟悉,代码出现问题时不善于调试查找,而是自己在哪里找半天,期中考试最终只拿到及格分,原因是对期中考试前的Comparable和Comparator接口知识没有及时加强巩固,导致考试时不太会用,编译都不能通过。随堂测验时,不选择调试查找代码问题,导致入门第一题花费太长时间解决结果错误问题。所以,在今后编程过程中还是要注意时间效率的问题。

另外,本阶段的题目集训练后,我对面向对象编程的概念有了进一步的理解,能够熟练运用类、对象、继承、多态、接口等进行编写代码。经过该阶段的学习,我学到了java数据结构中的栈的相关知识,如进出栈方法,先进后出原则等。还学到了java集合框架,其主要包括两种类型的容器,一种是集合(Collection),储存一个元素集合,另一种是图(Map),储存键/值对映射。主要学习的是具体实现类HashSet和HashMap的相关知识点,对此,我掌握了添加add()方法、移除remove()等基础方法,还掌握了两个类的异同:HashSet 基于 HashMap 来实现的,是一个不允许有重复元素的集合;HashSet 允许有 null 值。

而且能运用其实现简单的图形界面和动画。对以上的知识掌握都比较浅显,以后还需要继续研究学习,学得更深更精才行。

最后对教师、课程、作业、实验、作业、课上即课下组织方式等方面,我有以下改进建议:

1、希望老师能够提供更多实例和案例讲解,帮助学生更好地理解和运用所学知识。

2、希望老师对实验和作业中我们出现问题较多的地方进行提示或讲解。

posted @ 2023-06-28 15:26  乾为天、  阅读(8)  评论(0)    收藏  举报