22207320-王攀-Blog2

题目集4~6的总结性Blog
一、前言
经过题目集4至6的练习,我对Java编程的理解和实践能力都有了显著的提升。题目集4主要考察了继承与正则表达式的知识点,题目集5引入了家庭电路的模拟,题目集6则在前者的基础上增加了并联电路的处理。三次题目集的题量逐步增加,难度也有所提升,特别是题目集6,只有一题,但涉及的知识点较为复杂,需要深入理解电路原理以及Java中复杂的类与接口的设计。1
二、设计与分析
题目集4:数据处理与判题程序
在这个题目集中,我们实现了一个能够处理多选题和填空题的判题程序。主要功能包括题目的管理、学生的答题管理、评分和输出结果。以下是主要类和方法的介绍:

Question 类
封装了题目的基本属性,如编号、内容、标准答案等。
方法 matchAnswer 用于判断学生的答案是否正确。
方法 isPartiallyCorrect 用于判断学生的答案是否部分正确。
MultipleChoiceQuestion 类 和 FillInTheBlankQuestion 类
分别继承自 Question 类,用于处理多选题和填空题的特殊需求。
TestPaper 类
用于管理试卷,包括题目的集合和每题的分值。
方法 checkTotalScore 检查试卷总分是否为100分。
方法 checkQuestionExistence 检查试卷中是否存在指定的题目。
AnswerPaper 类
表示学生的答卷,包含了学生信息、试卷信息和答案列表。
Judge 类
负责评分和输出结果,通过调用不同的评估方法来处理不同类型题目的评分。
InputHandler 类
处理输入数据,将其解析为程序可以处理的对象。
主要代码示例:
class Question {
private int number;
private String content;
private String answer;
private boolean isValid = true;
private boolean isMultipleChoice;

public Question(int number, String content, String answer, boolean isMultipleChoice) {
    this.number = number;
    this.content = content;
    this.answer = answer;
    this.isMultipleChoice = isMultipleChoice;
}

public int getNumber() {
    return number;
}

public String getContent() {
    return content;
}

public String getAnswer() {
    return answer;
}

public void invalidate() {
    isValid = false;
}

public boolean isValid() {
    return isValid;
}

public boolean isMultipleChoice() {
    return isMultipleChoice;
}

public boolean matchAnswer(String studentAnswer) {
    return answer.equalsIgnoreCase(studentAnswer);
}

public boolean isPartiallyCorrect(String studentAnswer) {
    if (isMultipleChoice) {
        Set<String> correctSet = new HashSet<>(Arrays.asList(answer.split(" ")));
        Set<String> studentSet = new HashSet<>(Arrays.asList(studentAnswer.split(" ")));
        if (correctSet.equals(studentSet)) {
            return false; // 完全正确
        }
        if (Collections.disjoint(correctSet, studentSet)) {
            return false; // 完全错误
        }
        return correctSet.containsAll(studentSet) && studentSet.size() < correctSet.size();
    } else {
        return answer.contains(studentAnswer) && !studentAnswer.equals(answer);
    }
}

}

class TestPaper {
private int number;
private Map<Integer, Integer> questionScores = new HashMap<>();

public TestPaper(int number) {
    this.number = number;
}

public void addQuestion(int questionNumber, int score) {
    questionScores.put(questionNumber, score);
}

public boolean checkTotalScore() {
    int totalScore = questionScores.values().stream().mapToInt(Integer::intValue).sum();
    if (totalScore != 100) {
        System.out.println("alert: full score of test paper " + number + " is not 100 points");
        return false;
    }
    return true;
}

public boolean checkQuestionExistence(Map<Integer, Question> questions) {
    for (int qNumber : questionScores.keySet()) {
        if (!questions.containsKey(qNumber)) {
            return false;
        }
    }
    return true;
}

public int getNumber() {
    return number;
}

public Map<Integer, Integer> getQuestionScores() {
    return questionScores;
}

}

class Answer {
private int paperNumber;
private String studentId;
private Map<Integer, String> answers = new HashMap<>();

public Answer(int paperNumber, String studentId) {
    this.paperNumber = paperNumber;
    this.studentId = studentId;
}

public void addAnswer(int questionNumber, String answer) {
    answers.put(questionNumber, answer);
}

public String getStudentId() {
    return studentId;
}

public int getPaperNumber() {
    return paperNumber;
}

public Map<Integer, String> getAnswers() {
    return answers;
}

}
设计类图:
顺序图:

题目集五:家居电路模拟
为了实现智能家居强电电路模拟系统,我设计了以下几个类和方法:

Device:抽象类,表示一个设备,包含设备的基本属性和方法。
Switch:继承自Device,表示一个开关。
Fan:继承自Device,表示一个风扇。
Bulb:继承自Device,表示一个灯具。
Circuit:表示一个电路,包含设备和连接关系的管理。
Main:主类,负责读取输入命令并调用Circuit类的方法进行处理。
2. 关键类和方法解析
Device 类
abstract class Device {
String id; // 设备标识符
double resistance; // 电阻值
int voltageDifference; // 引脚间的电压差

// 构造函数,初始化设备ID和电阻
Device(String id, double resistance) {
    this.id = id;
    this.resistance = resistance;
    this.voltageDifference = 0; // 默认电压差为0
}

// 更新设备状态的方法,由子类实现
abstract void updateState(String command);

// 获取设备当前状态的方法,子类重写来根据设备的实际状态返回信息
abstract String getStatus();

// 设置电压差
void setVoltageDifference(int voltage) {
    this.voltageDifference = voltage;
}

}
Switch 类
class Switch extends Device {
boolean isClosed; // 开关状态(关闭时为true)

// 构造函数初始化开关状态
Switch(String id) {
    super(id, 0); // 开关的电阻是0
    this.isClosed = false; // 默认状态为“打开”
}

@Override
void updateState(String command) {
    isClosed = !isClosed; // 每次切换开关状态
}

@Override
String getStatus() {
    // 根据开关状态返回相应的状态文本
    return isClosed ? "closed" : "turned on";
}

}
Fan 类
class Fan extends Device {
int minVoltage, maxVoltage; // 风扇工作电压范围
int minSpeed, maxSpeed; // 风扇转速范围

// 构造函数初始化风扇参数
Fan(String id, double resistance, int minVoltage, int maxVoltage, int minSpeed, int maxSpeed) {
    super(id, resistance);
    this.minVoltage = minVoltage;
    this.maxVoltage = maxVoltage;
    this.minSpeed = minSpeed;
    this.maxSpeed = maxSpeed;
}

@Override
void updateState(String command) {
    // 风扇的状态是由电压差来决定的,不需要在这里手动更新
}

@Override
String getStatus() {
    if (voltageDifference < minVoltage) return "0"; // 停止
    if (voltageDifference > maxVoltage) return String.valueOf(maxSpeed); // 达到最大转速
    // 计算转速比例
    double speed = minSpeed + (double) (voltageDifference - minVoltage) / (maxVoltage - minVoltage) * (maxSpeed - minSpeed);
    return String.valueOf((int) speed); // 返回整数值
}

}
Bulb 类
class Bulb extends Device {
int maxBrightness; // 最大亮度

// 构造函数初始化灯具参数
Bulb(String id, double resistance, int maxBrightness) {
    super(id, resistance);
    this.maxBrightness = maxBrightness;
}

@Override
void updateState(String command) {
    // 灯具的状态由电压差来决定,不需要手动更新
}

@Override
String getStatus() {
    if (voltageDifference == 0) return "0"; // 灯灭
    double brightness = (double) voltageDifference / 220 * maxBrightness;
    return String.valueOf((int) brightness); // 亮度按比例计算
}

}
Circuit 类

class Circuit {
Map<String, Device> devices = new LinkedHashMap<>();
Map<String, List> connections = new HashMap<>();

// 添加设备到电路中
void addDevice(Device device) {
    devices.put(device.id, device);
}

// 连接设备的引脚
void addConnection(String pin1, String pin2) {
    connections.computeIfAbsent(pin1, k -> new ArrayList<>()).add(pin2);
    connections.computeIfAbsent(pin2, k -> new ArrayList<>()).add(pin1);
}

// 根据命令更新设备的状态
void updateDevice(String command) {
    String id = command.substring(1, 3); // 提取设备ID
    Device device = devices.get(id);
    if (device != null) {
        device.updateState(command);
    }
}

// 模拟电路的工作
void simulate() {
    // 假设电源电压为220V
    for (Device device : devices.values()) {
        device.setVoltageDifference(220); // 给所有设备设置电压差为220V
    }
}

// 输出所有设备的状态
void outputStatus() {
    for (Device device : devices.values()) {
        System.out.println("@" + device.id + ":" + device.getStatus());
    }
}

}
Main 类
public class Main {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
Circuit circuit = new Circuit();

    // 读取输入并进行处理
    while (scanner.hasNextLine()) {
        String input = scanner.nextLine().trim();
        if (input.equals("end")) break; // 结束输入

        if (input.startsWith("#")) {
            // 处理控制命令,如#K1,#F1+等
            circuit.updateDevice(input);
        } else if (input.startsWith("[")) {
            // 处理连接信息,如:[K1-1 K2-2]
            String[] pins = input.substring(1, input.length() - 1).split(" ");
            circuit.addConnection(pins[0], pins[1]);
        } else if (input.contains(":")) {
            // 处理设备定义,如:K1:0
            String[] parts = input.split(":");
            if (parts[0].startsWith("K")) {
                circuit.addDevice(new Switch(parts[0]));
            } else if (parts[0].startsWith("D")) {
                circuit.addDevice(new Bulb(parts[0], 10, 200)); // 示例:白炽灯
            } else if (parts[0].startsWith("A")) {
                circuit.addDevice(new Fan(parts[0], 20, 80, 150, 80, 360)); // 示例:吊扇
            }
        }
    }

    // 模拟电路并输出设备状态
    circuit.simulate();
    circuit.outputStatus();
}

}
设计类图:
顺序图:

题目集6:复杂电路模拟
在这个题目集中,我们在题目集5的基础上增加了并联电路的处理。系统的主要功能包括处理复杂的电路连接关系、更精细的设备操作逻辑、电路分析相关功能的强化等。以下是主要类和方法的介绍:

Device 类
抽象类,表示电路中的基本设备。
包含设备ID、电阻值和电压差属性。
抽象方法 updateState 和 getStatus 由子类实现。
Switch 类
继承自 Device,表示开关设备。
属性 isClosed 表示开关状态(关闭时为 true)。
方法 updateState 切换开关状态。
方法 getStatus 返回开关的当前状态。
Fan 类
继承自 Device,表示风扇设备。
属性 minVoltage, maxVoltage, minSpeed, maxSpeed 表示风扇的工作电压范围和转速范围。
方法 updateState 不需要手动更新状态。
方法 getStatus 根据电压差计算风扇的转速并返回。
Bulb 类
继承自 Device,表示灯具设备。
属性 maxBrightness 表示最大亮度。
方法 updateState 不需要手动更新状态。
方法 getStatus 根据电压差计算灯具的亮度并返回。
Circuit 类
管理设备和连接信息,提供方法来更新设备状态和模拟电路。
方法 addDevice 添加设备到电路中。
方法 addConnection 连接设备的引脚。
方法 updateDevice 根据命令更新设备的状态。
方法 simulate 模拟电路的工作。
方法 outputStatus 输出所有设备的状态。
主要代码示例:

abstract class Device {
String id; // 设备标识符
double resistance; // 电阻值
int voltageDifference; // 引脚间的电压差

Device(String id, double resistance) {
    this.id = id;
    this.resistance = resistance;
    this.voltageDifference = 0; // 默认电压差为0
}

abstract void updateState(String command);

abstract String getStatus();

void setVoltageDifference(int voltage) {
    this.voltageDifference = voltage;
}

}

class Switch extends Device {
boolean isClosed; // 开关状态(关闭时为true)

Switch(String id) {
    super(id, 0); // 开关的电阻是0
    this.isClosed = false; // 默认状态为“打开”
}

@Override
void updateState(String command) {
    isClosed = !isClosed; // 每次切换开关状态
}

@Override
String getStatus() {
    return isClosed ? "closed" : "turned on";
}

}

class Fan extends Device {
int minVoltage, maxVoltage; // 风扇工作电压范围
int minSpeed, maxSpeed; // 风扇转速范围

Fan(String id, double resistance, int minVoltage, int maxVoltage, int minSpeed, int maxSpeed) {
    super(id, resistance);
    this.minVoltage = minVoltage;
    this.maxVoltage = maxVoltage;
    this.minSpeed = minSpeed;
    this.maxSpeed = maxSpeed;
}

@Override
void updateState(String command) {
    // 风扇的状态是由电压差来决定的,不需要在这里手动更新
}

@Override
String getStatus() {
    if (voltageDifference < minVoltage) return "0"; // 停止
    if (voltageDifference > maxVoltage) return String.valueOf(maxSpeed); // 达到最大转速
    double speed = minSpeed + (double) (voltageDifference - minVoltage) / (maxVoltage - minVoltage) * (maxSpeed - minSpeed);
    return String.valueOf((int) speed); // 返回整数值
}

}

class Bulb extends Device {
int maxBrightness; // 最大亮度

Bulb(String id, double resistance, int maxBrightness) {
    super(id, resistance);
    this.maxBrightness = maxBrightness;
}

@Override
void updateState(String command) {
    // 灯具的状态由电压差来决定,不需要手动更新
}

@Override
String getStatus() {
    if (voltageDifference == 0) return "0"; // 灯灭
    double brightness = (double) voltageDifference / 220 * maxBrightness;
    return String.valueOf((int) brightness); // 亮度按比例计算
}

}

class Circuit {
Map<String, Device> devices = new LinkedHashMap<>();
Map<String, List> connections = new HashMap<>();

void addDevice(Device device) {
    devices.put(device.id, device);
}

void addConnection(String pin1, String pin2) {
    connections.computeIfAbsent(pin1, k -> new ArrayList<>()).add(pin2);
    connections.computeIfAbsent(pin2, k -> new ArrayList<>()).add(pin1);
}

void updateDevice(String command) {
    String id = command.substring(1, 3); // 提取设备ID
    Device device = devices.get(id);
    if (device != null) {
        device.updateState(command);
    }
}

void simulate() {
    for (Device device : devices.values()) {
        device.setVoltageDifference(220); // 给所有设备设置电压差为220V
    }
}

void outputStatus() {
    for (Device device : devices.values()) {
        System.out.println("@" + device.id + ":" + device.getStatus());
    }
}

}

public class Main {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
Circuit circuit = new Circuit();

    while (scanner.hasNextLine()) {
        String input = scanner.nextLine().trim();
        if (input.equals("end")) break; // 结束输入

        if (input.startsWith("#")) {
            circuit.updateDevice(input);
        } else if (input.startsWith("[")) {
            String[] pins = input.substring(1, input.length() - 1).split(" ");
            circuit.addConnection(pins[0], pins[1]);
        } else if (input.contains(":")) {
            String[] parts = input.split(":");
            if (parts[0].startsWith("K")) {
                circuit.addDevice(new Switch(parts[0]));
            } else if (parts[0].startsWith("D")) {
                circuit.addDevice(new Bulb(parts[0], 10, 200)); // 示例:白炽灯
            } else if (parts[0].startsWith("A")) {
                circuit.addDevice(new Fan(parts[0], 20, 80, 150, 80, 360)); // 示例:吊扇
            }
        }
    }

    circuit.simulate();
    circuit.outputStatus();
}

}
设计类图:

顺序图:
三、踩坑心得
在完成题目集4至6的过程中,我积累了丰富的经验和教训,这些经验教训不仅帮助我顺利完成了任务,也为我后续的学习和工作打下了坚实的基础。

题目集4
正则表达式的复杂性与可维护性

在处理输入数据时,我最初尝试使用非常复杂的正则表达式来确保输入的格式正确。然而,这种做法很快就暴露出了问题。复杂的正则表达式不仅难以编写,而且一旦出现错误,调试起来也非常困难。为了解决这个问题,我采取了以下措施:

简化正则表达式:将复杂的正则表达式拆分成多个简单的表达式,每个表达式只处理一部分输入格式。这样做不仅使代码更易读,也更容易调试和维护。
增加条件判断:在正则表达式匹配的基础上,增加了更多的条件判断,以确保输入数据的合法性。例如,检查输入的数字是否在合理范围内,检查字符串是否符合预期的格式等。
输入数据的错误处理

在处理用户输入时,经常会遇到各种意外情况,如格式错误、缺失字段等。为了提高程序的健壮性,我采用了以下策略:

异常处理:使用 try-catch 块来捕获和处理输入中的异常情况。这样可以避免程序因输入错误而崩溃,同时也能给用户提供明确的错误提示。
错误信息记录:使用 StringBuilder 来收集和记录所有的错误信息,最后一次性输出给用户。这样做不仅提高了用户体验,也方便了调试。
题目集5和6
电路原理的理解

在进行电路模拟时,我最初对电路原理的理解不够深入,导致在计算电压传递和电流分配时出现了很多错误。为了解决这个问题,我采取了以下措施:

查阅资料:通过查阅电路原理相关的书籍和在线资源,加深了对电路基础知识的理解。
反复试验:通过编写测试用例,反复试验不同的电路配置,逐步修正算法中的错误。
代码重构:在理解电路原理的基础上,对代码进行了重构,使其更加清晰和高效。例如,将电压传递和电流分配的计算逻辑分离出来,放在独立的方法中,便于管理和维护。
异常处理

在处理复杂的电路网络时,输入错误和未知设备类型是常见的问题。为了优雅地处理这些问题,我采用了以下策略:

输入验证:在接收用户输入时,首先进行严格的格式验证,确保输入数据的合法性。
设备类型检查:在创建设备对象时,检查设备类型是否合法。如果设备类型未知,则抛出异常并给出明确的错误提示。
异常捕获:在关键的计算逻辑中,使用 try-catch 块来捕获可能发生的异常,确保程序不会因为某个错误而完全停止运行。
四、总结
通过完成题目集4至6,我在编程技能和问题解决能力方面取得了显著的进步。以下是我在整个学习过程中的几点体会和收获:

基础知识的重要性:无论是数据处理还是电路模拟,扎实的基础知识都是解决问题的关键。在遇到难题时,回归基础往往能找到突破口。
代码的可维护性:编写可维护的代码不仅有助于自己未来的开发工作,也能方便他人理解和修改。通过模块化和复用性设计,可以使代码更加清晰和高效。
调试技巧:调试是编程中不可或缺的一部分。学会使用调试工具和编写测试用例,可以大大提高开发效率,减少错误的发生。
团队合作:在学习过程中,与其他同学交流和合作是非常重要的。通过讨论和分享,可以互相启发,共同进步。
持续学习:技术是不断发展的,只有保持持续学习的态度,才能跟上时代的步伐。无论是阅读最新的技术文章,还是参加线上课程,都是提升自己的有效途径。
五、对教师和课程的建议
增加实际案例:在课程中增加更多实际案例的讲解,帮助学生更好地将理论知识应用于实践中。实际案例可以来自真实世界的问题,也可以是经典的编程挑战。
定期举办编程比赛:通过举办编程比赛或项目展示活动,激发学生的学习兴趣,促进同学间的交流和合作。比赛可以设置不同的难度级别,适合不同水平的学生参与。
提供更多资源:提供更多的学习资源,如参考书籍、在线教程和开源项目,帮助学生在课后继续学习和探索。
鼓励创新思维:在教学过程中,鼓励学生发挥创新思维,提出独特的解决方案。可以通过小组讨论、头脑风暴等方式,培养学生的创造力和批判性思维。
通过以上总结和建议,希望未来的学习和教学能够更加高效和有趣。。可以通过小组讨论、头脑风暴等方式,培养学生的创造力和批判性思维。

posted @   天意不可违123  阅读(18)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· AI 智能体引爆开源社区「GitHub 热点速览」
· C#/.NET/.NET Core技术前沿周刊 | 第 29 期(2025年3.1-3.9)
· 从HTTP原因短语缺失研究HTTP/2和HTTP/3的设计差异
点击右上角即可分享
微信分享提示