代码结构构思
文件结构
student_management_system/
│
├── main.py # 主函数入口
├── manager.py # 学生管理类(增删改查功能)
└── models.py # 学生模型类
功能描述
添加学生:
- 输入学号、姓名和年龄,新增一个学生。
- 如果学号重复,则提示添加失败。
删除学生:
- 输入学号,根据学号删除学生。
- 如果学号不存在,则提示删除失败。
修改学生信息:
- 输入学号,可选择修改学生的姓名和/或年龄。
查询学生信息:
- 根据学号查找并打印学生信息。
显示所有学生:
- 列出所有学生的详细信息。
退出系统:
- 结束程序运行。
扩展建议
持久化数据:
- 使用文件(如
JSON或CSV)保存学生信息,退出系统时保存数据,下次运行时加载。
异常处理:
- 添加输入校验和异常捕获(如年龄输入非数字时提示用户)。
初级代码
下面是一个简单的学生管理系统的代码实现,仅仅使用面向对象实现了基本的功能
模型类:models.py
class Student:
"""
学生模型类,包含学生的基本信息:姓名、年龄、学号
"""
def __init__(self, student_id, name, age):
self.student_id = student_id
self.name = name
self.age = age
def __str__(self):
return f"学号: {self.student_id}, 姓名: {self.name}, 年龄: {self.age}"
学生管理类:manager.py
from models import Student
class StudentManager:
"""
学生管理类,提供增删改查功能
"""
def __init__(self):
self.students = [] # 存储所有学生对象的列表
def add_student(self, student_id, name, age):
"""添加学生"""
student = Student(student_id, name, age)
self.students.append(student)
print(f"添加成功: {student}")
def remove_student(self, student_id):
"""根据学号删除学生"""
for student in self.students:
if student.student_id == student_id:
self.students.remove(student)
print(f"已删除: {student}")
return
print(f"学号为 {student_id} 的学生不存在")
def update_student(self, student_id, name=None, age=None):
"""根据学号更新学生信息"""
for student in self.students:
if student.student_id == student_id:
if name:
student.name = name
if age:
student.age = age
print(f"更新成功: {student}")
return
print(f"学号为 {student_id} 的学生不存在")
def find_student(self, student_id):
"""根据学号查找学生"""
for student in self.students:
if student.student_id == student_id:
print(f"找到学生: {student}")
return student
print(f"学号为 {student_id} 的学生不存在")
return None
def list_students(self):
"""列出所有学生"""
if not self.students:
print("当前没有学生信息")
else:
print("所有学生信息如下:")
for student in self.students:
print(student)
主函数入口:main.py
from manager import StudentManager
def print_menu():
"""打印菜单"""
print("\n学生管理系统")
print("1. 添加学生")
print("2. 删除学生")
print("3. 修改学生信息")
print("4. 查询学生信息")
print("5. 显示所有学生")
print("6. 退出系统")
def main():
manager = StudentManager() # 创建学生管理对象
while True:
print_menu()
choice = input("请选择操作(1-6): ")
if choice == "1":
student_id = input("请输入学号: ")
name = input("请输入姓名: ")
age = input("请输入年龄: ")
manager.add_student(student_id, name, int(age))
elif choice == "2":
student_id = input("请输入要删除的学生学号: ")
manager.remove_student(student_id)
elif choice == "3":
student_id = input("请输入要修改的学生学号: ")
name = input("请输入新姓名(可留空跳过修改): ")
age = input("请输入新年龄(可留空跳过修改): ")
manager.update_student(student_id, name if name else None, int(age) if age else None)
elif choice == "4":
student_id = input("请输入要查询的学生学号: ")
manager.find_student(student_id)
elif choice == "5":
manager.list_students()
elif choice == "6":
print("退出系统")
break
else:
print("输入有误,请重新选择!")
if __name__ == "__main__":
main()
添加扩展功能:
在基于基本功能的基础上,添加了持久化数据功能(使用 JSON 文件保存和加载学生信息)以及异常处理(包括输入校验和异常捕获),实现更可靠和功能完善的学生管理系统。
具体要求:
优化后的代码主要实现了以下几个功能:
- 数据持久化:
- 使用JSON文件来持久化学生数据,重新启动程序后,之前保存的学生信息仍然可以加载并使用。
StudentManager类中添加load_students和save_students方法,用于在程序启动时加载数据和在退出时保存数据。
- 数据转换:
Student类增加to_dict和from_dict方法,以便学生对象与JSON数据之间进行转换。
- 输入验证:
- 在
main.py中,添加get_valid_int函数来确保用户输入的年龄是一个有效的整数,避免程序崩溃。
- 在
- 异常处理:
- 在数据加载和保存过程中加入异常处理,确保即使数据文件不存在或者文件格式错误,程序也能继续运行。
- 在数据保存时,如果出现其他异常情况,则会输出错误信息。
- 菜单修改:
- 更新菜单中的选项:退出系统改为“保存并退出系统”,提示用户保存数据。
- 逻辑优化:
- 更新学生信息时,进行更细致的输入验证,确保输入的年龄如果为空,则不会尝试转换成整数。
持久化数据功能如何实现?
data = [student.to_dict() for student in self.students]
这段代码是一个 列表推导式(List Comprehension),用于将 self.students(一个学生对象的列表)转换成包含学生字典的列表。下面逐步解析:
1. 基础部分:self.students
self.students 是一个存储 学生对象 的列表,例如:
self.students = [
Student("001", "Alice", 18),
Student("002", "Bob", 19)
]
这是一个包含 Student 对象的列表。
2. 调用 student.to_dict()
student.to_dict() 是一个方法,用于将 Student 对象转换为 字典。
在代码中的 Student 类里,to_dict() 可以是这样定义的:
def to_dict(self):
"""将学生对象转换为字典"""
return {"student_id": self.student_id, "name": self.name, "age": self.age}
调用 to_dict() 后,一个 Student 对象会变成这样的字典:
{"student_id": "001", "name": "Alice", "age": 18}
3. 列表推导式的作用
列表推导式将 self.students 中的每个 Student 对象转换成字典,并返回一个新列表。
代码含义:
data = [student.to_dict() for student in self.students]
等价的普通循环代码如下:
data = []
for student in self.students:
data.append(student.to_dict())
- 遍历
self.students中的每个student对象。 - 对每个
student调用to_dict()方法,生成对应的字典。 - 将所有字典组成一个新的列表,赋值给
data
示例: 假设 self.students 的内容为:
self.students = [
Student("001", "Alice", 18),
Student("002", "Bob", 19)
]
那么执行这段代码后,data 的值为:
data = [
{"student_id": "001", "name": "Alice", "age": 18},
{"student_id": "002", "name": "Bob", "age": 19}
]
这种转换通常用于 数据持久化 或 数据传输,例如:
- 将数据保存到 JSON 文件。
- 将数据发送到 API 或数据库。
如何持久化字典到json 文件中?
例如,设置在 save_students() 方法中,使用这段代码将学生对象序列化为 JSON 数据:
with open(self.DATA_FILE, "w", encoding="utf-8") as file:
data = [student.to_dict() for student in self.students]
json.dump(data, file, ensure_ascii=False, indent=4)
结果是一个 JSON 文件:
[
{
"student_id": "001",
"name": "Alice",
"age": 18
},
{
"student_id": "002",
"name": "Bob",
"age": 19
}
]
如何加载已持久化的 json 文件中的内容转化为字典列表?
要将一个已持久化的 JSON 文件加载并转化为字典列表,可以使用 Python 的 json 模块。假设你的 JSON 文件中存储的数据是一个列表,其中每个元素都是一个字典,如你所描述的结构。以下是步骤和代码示例:
- 确保 JSON 文件的结构正确,数据内容看起来应该类似于:
[
{"student_id": "001", "name": "Alice", "age": 18},
{"student_id": "002", "name": "Bob", "age": 19},
{"student_id": "003", "name": "Charlie", "age": 17}
]
- 使用 Python 代码读取文件并加载为列表:
import json
# 假设你的 JSON 文件名为 'students.json'
with open('students.json', 'r', encoding='utf-8') as file:
data = json.load(file)
# 打印加载的列表
print(data)
在这个例子中,json.load(file) 函数会读取文件内容并将其解析为字典列表。请确保在使用 open() 函数时指定正确的文件路径和编码(通常为 utf-8,尤其是在处理可能包含非 ASCII 字符的数据时)。
这段代码,data 变量将包含文件中的数据
当然,我们可以选择优化一下代码,添加异常处理:
import json
# 假设 JSON 文件路径为 'students.json'
file_path = "students.json"
try:
# 尝试打开并读取 JSON 文件
with open(file_path, 'r', encoding='utf-8') as file:
data = json.load(file)
# 此时 data 已经是一个 Python 列表,包含字典元素
print(data)
except FileNotFoundError:
print(f"文件路径错误: {file_path} 找不到。")
except json.JSONDecodeError:
print("JSON 格式错误,无法解析文件。")
输出结果:

如何从字典转换为学生对象?
字典 转换为 Student 对象。可以使用一个 工厂方法,用来简化从外部数据结构创建 Student 实例的过程。
1. data 是什么?
data 是一个包含多个字典的列表,每个字典表示一个学生的信息。例如:
data = [
{"student_id": "001", "name": "Alice", "age": 18},
{"student_id": "002", "name": "Bob", "age": 19},
{"student_id": "003", "name": "Charlie", "age": 17}
]
2. Student.from_dict(item)
def from_dict(data):
"""从字典转换为学生对象"""
return Student(data["student_id"], data["name"], data["age"])
Student.from_dict(item) 是调用 Student 类中的静态方法,用字典 item 创建一个新的 Student 对象。假设 item 是:
{"student_id": "001", "name": "Alice", "age": 18}
则 Student.from_dict(item) 等价于:
Student("001", "Alice", 18)
3. 列表推导式
在这里:
- 表达式 是
Student.from_dict(item),表示将每个item转换为Student对象。 - 变量 是
item,表示data列表中的每一个字典。 - 可迭代对象 是
data,它是包含学生数据的字典列表。
最终,这段代码会返回一个由 Student 对象组成的新列表。
4. 完整流程
- 对于
data列表中的每个item(即每个学生信息字典),都会调用Student.from_dict(item),将其转换为Student对象。 - 生成的新
Student对象会被收集到一个列表中。 - 最终,这个列表被赋值给
self.students,即self.students中存储了所有学生的对象。
我们可以先写一个简单的转化代码感受下,再带入实战:
class Student:
def __init__(self, student_id, name, age):
self.student_id = student_id
self.name = name
self.age = age
@staticmethod
def from_dict(data_slice):
"""从字典的切片中转换为学生对象"""
return Student(data_slice["student_id"], data_slice["name"], data_slice["age"])
# 原始数据
data = [
{"student_id": "001", "name": "Alice", "age": 18},
{"student_id": "002", "name": "Bob", "age": 19},
{"student_id": "003", "name": "Charlie", "age": 17}
]
# 转换为对象列表
students = [Student.from_dict(data_slice) for data_slice in data]
print(students)
输出结果:

修改后代码内容:
1、模型类:models.py
模型类保持不变,表示学生的基本信息。
class Student:
"""
学生模型类,包含学生的基本信息:姓名、年龄、学号
"""
def __init__(self, student_id, name, age):
self.student_id = student_id
self.name = name
self.age = age
def __str__(self):
return f"学号: {self.student_id}, 姓名: {self.name}, 年龄: {self.age}"
def to_dict(self):
"""将学生对象转换为字典,便于持久化"""
return {"student_id": self.student_id, "name": self.name, "age": self.age}
@staticmethod
def from_dict(data):
"""从字典转换为学生对象"""
return Student(data["student_id"], data["name"], data["age"])
2. 学生管理类:manager.py
优化的学生管理类,支持加载和保存数据到 JSON 文件,并添加异常处理。
import json
from models import Student
class StudentManager:
"""
学生管理类,提供增删改查功能,并支持数据持久化
"""
DATA_FILE = "students.json" # 保存数据的文件路径
def __init__(self):
self.students = [] # 存储所有学生对象的列表
self.load_students() # 初始化时加载数据
def load_students(self):
"""从文件加载学生数据"""
try:
with open(self.DATA_FILE, "r", encoding="utf-8") as file:
data = json.load(file)
self.students = [Student.from_dict(item) for item in data]
print("学生数据加载成功!")
except FileNotFoundError:
print("数据文件不存在,已创建新的数据文件。")
self.students = []
except json.JSONDecodeError:
print("数据文件格式错误,已清空数据。")
self.students = []
def save_students(self):
"""将学生数据保存到文件"""
try:
with open(self.DATA_FILE, "w", encoding="utf-8") as file:
data = [student.to_dict() for student in self.students]
json.dump(data, file, ensure_ascii=False, indent=4)
print("学生数据已保存!")
except Exception as e:
print(f"保存数据时出现错误:{e}")
def add_student(self, student_id, name, age):
"""添加学生"""
student = Student(student_id, name, age)
self.students.append(student)
print(f"添加成功: {student}")
def remove_student(self, student_id):
"""根据学号删除学生"""
for student in self.students:
if student.student_id == student_id:
self.students.remove(student)
print(f"已删除: {student}")
return
print(f"学号为 {student_id} 的学生不存在")
def update_student(self, student_id, name=None, age=None):
"""根据学号更新学生信息"""
for student in self.students:
if student.student_id == student_id:
if name:
student.name = name
if age:
student.age = age
print(f"更新成功: {student}")
return
print(f"学号为 {student_id} 的学生不存在")
def find_student(self, student_id):
"""根据学号查找学生"""
for student in self.students:
if student.student_id == student_id:
print(f"找到学生: {student}")
return student
print(f"学号为 {student_id} 的学生不存在")
return None
def list_students(self):
"""列出所有学生"""
if not self.students:
print("当前没有学生信息")
else:
print("所有学生信息如下:")
for student in self.students:
print(student)
3. 主函数入口:main.py
主函数入口中添加了异常处理和输入校验,确保系统更加稳定。
from manager import StudentManager
def print_menu():
"""打印菜单"""
print("\n学生管理系统")
print("1. 添加学生")
print("2. 删除学生")
print("3. 修改学生信息")
print("4. 查询学生信息")
print("5. 显示所有学生")
print("6. 保存并退出系统")
def get_valid_int(prompt):
"""获取有效的整数输入"""
while True:
try:
value = int(input(prompt))
return value
except ValueError:
print("输入无效,请输入一个整数!")
def main():
manager = StudentManager() # 创建学生管理对象
while True:
print_menu()
choice = input("请选择操作(1-6): ")
if choice == "1":
student_id = input("请输入学号: ")
name = input("请输入姓名: ")
age = get_valid_int("请输入年龄: ")
manager.add_student(student_id, name, age)
elif choice == "2":
student_id = input("请输入要删除的学生学号: ")
manager.remove_student(student_id)
elif choice == "3":
student_id = input("请输入要修改的学生学号: ")
name = input("请输入新姓名(可留空跳过修改): ")
age = input("请输入新年龄(可留空跳过修改): ")
manager.update_student(
student_id,
name if name else None,
int(age) if age.isdigit() else None
)
elif choice == "4":
student_id = input("请输入要查询的学生学号: ")
manager.find_student(student_id)
elif choice == "5":
manager.list_students()
elif choice == "6":
manager.save_students()
print("退出系统")
break
else:
print("输入有误,请重新选择!")
if __name__ == "__main__":
main()
代码改进点总结:
持久化功能:
- 使用 JSON 文件保存和加载学生信息,退出系统时自动保存数据,下次启动时自动加载。
异常处理:
- 提供输入校验,如验证年龄是否为整数。
- 捕获文件操作中的异常(如文件不存在、JSON 格式错误)。
- 对关键逻辑的异常进行友好提示。
代码可扩展性:
Student类支持字典与对象的转换,方便扩展到其他数据格式(如 CSV 或数据库)。- 数据文件路径
DATA_FILE是可配置的。
优化代码算法
可以使用字典映射操作函数的方法,简化冗长的多分支 if-elif 逻辑。通过将用户输入的选项与对应的功能逻辑绑定到一个字典中,可以让代码更加简洁、清晰和易于维护。
优化后的主函数入口代码:main.py
from manager import StudentManager
def print_menu():
"""打印菜单"""
print("\n学生管理系统")
print("1. 添加学生")
print("2. 删除学生")
print("3. 修改学生信息")
print("4. 查询学生信息")
print("5. 显示所有学生")
print("6. 保存并退出系统")
def get_valid_int(prompt):
"""获取有效的整数输入"""
while True:
try:
value = int(input(prompt))
return value
except ValueError:
print("输入无效,请输入一个整数!")
def add_student(manager):
student_id = input("请输入学号: ")
name = input("请输入姓名: ")
age = get_valid_int("请输入年龄: ")
manager.add_student(student_id, name, age)
def remove_student(manager):
student_id = input("请输入要删除的学生学号: ")
manager.remove_student(student_id)
def update_student(manager):
student_id = input("请输入要修改的学生学号: ")
name = input("请输入新姓名(可留空跳过修改): ")
age = input("请输入新年龄(可留空跳过修改): ")
manager.update_student(
student_id,
name if name else None,
int(age) if age.isdigit() else None
)
def find_student(manager):
student_id = input("请输入要查询的学生学号: ")
manager.find_student(student_id)
def list_students(manager):
manager.list_students()
def save_and_exit(manager):
manager.save_students()
print("退出系统")
exit()
def main():
manager = StudentManager() # 创建学生管理对象
actions = {
"1": add_student,
"2": remove_student,
"3": update_student,
"4": find_student,
"5": list_students,
"6": save_and_exit,
}
while True:
print_menu()
choice = input("请选择操作(1-6): ")
action = actions.get(choice)
if action:
action(manager)
else:
print("输入有误,请重新选择!")
if __name__ == "__main__":
main()
优化后的特点
- 通过字典映射实现功能选择:
- 用户的输入选项(如
1、2、3等)作为字典的键。 - 功能函数(如
handle_add_student)作为字典的值。 - 根据用户输入调用字典中的对应函数,避免了大量冗长的
if-elif逻辑。
- 用户的输入选项(如
- 功能函数独立化:
- 每个功能模块(如添加学生、删除学生等)被封装成独立的函数。
- 主函数只负责菜单显示和根据用户选择调用对应的功能函数,逻辑更加清晰。
- 支持扩展性:
- 如果需要添加新的功能,只需定义一个新的功能函数,并将其添加到
operations字典中即可,无需修改主循环代码。
- 如果需要添加新的功能,只需定义一个新的功能函数,并将其添加到
- 代码简洁且易于维护:
- 主循环中的逻辑只有两部分:打印菜单和调用对应的功能函数。
- 函数间解耦,修改某个功能时不会影响其他功能。
字典来映射优化后续扩展功能示例
如果要新增功能,比如按年龄排序显示所有学生:
- 定义一个新的功能函数:
def handle_sort_students_by_age(manager):
"""按年龄排序并显示所有学生"""
sorted_students = sorted(manager.students, key=lambda s: s.age)
print("按年龄排序的学生信息如下:")
for student in sorted_students:
print(student)
将新功能添加到 operations 字典中:
operations = {
"1": handle_add_student,
"2": handle_remove_student,
"3": handle_update_student,
"4": handle_find_student,
"5": handle_list_students,
"6": handle_exit,
"7": handle_sort_students_by_age # 新增功能
}
更新菜单打印函数:
def print_menu():
print("\n学生管理系统")
print("1. 添加学生")
print("2. 删除学生")
print("3. 修改学生信息")
print("4. 查询学生信息")
print("5. 显示所有学生")
print("6. 保存并退出系统")
print("7. 按年龄排序显示学生")
通过这种结构化设计,新功能的添加只需定义一个函数,并修改少量代码即可实现。
发布者:LJH,转发请注明出处:https://www.ljh.cool/42159.html