教师关联专业

逻辑

当创建课程时,课程会自动关联到教师所属的专业
学生选课时,系统可以按专业筛选课程
在后台管理中,管理员可以按专业查看教师和课程情况

绑定关系:

每个教师必须选择一个所属专业

核心作用:

排课时:系统会自动限制教师只能开设本专业的课程
选课时:学生能看到授课教师的专业背景
管理时:可以按专业筛选教师名单

前端

Teacher.vue

1
2
3
4
5
6
7
8
9
10
11
<el-table-column label="所属专业" prop="specialityName"></el-table-column>

<el-form-item label="所属专业" prop="specialityId">
<el-select v-model="data.form.specialityId" placeholder="请选择专业" style="width: 100%">
<el-option v-for="item in data.specialityDate"
:key="item.id"
:label="item.name"
:value="item.id">
</el-option>
</el-select>
</el-form-item>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
const data = reactive({
// 教师信息弹窗对话框
formVisible: false,
// 教师信息表单数据
form: {
},
// 教师信息表格数据的数组,初始为空数组
tableData: [],
// 分页查询的页码
pageNum: 1,
// 分页查询的每页显示的记录数
pageSize: 5,
// 分页查询的总记录数,初始为0
total: 0,
// 教师姓名
name: null,
// 专业数据
specialityDate: [],
});

// 加载专业数据
const loadSpeciality = () => {
// 调用后端接口查询专业数据
// 这里可以使用axios或者其他请求库发送请求
// 例如:axios.get('/api/speciality/selectAll')
request.get('/speciality/selectAll').then(res => {
if (res.code === '200') {
// 将查询到的专业数据赋值给specialityDate
data.specialityDate = res.data
}else {
ElMessage.error(res.msg)
}
})
}

loadSpeciality()//一定要调用哦,不然没用

TeacherMapper.java

1
2
3
4
5
6
7
8
9
10
// 查询所有教师信息
@Select("select teacher.*, speciality.name as specialityName from teacher " +
"left join speciality on teacher.speciality_id = speciality.id")
List<Teacher> selectAll();

// 根据教师姓名查询教师信息,模糊查询
@Select("select teacher.*, speciality.name as specialityName from teacher " +
"left join speciality on teacher.speciality_id = speciality.id " +
"where teacher.name like concat('%',#{name},'%')")
List<Teacher> selectByName(String name);

学生关联学院

逻辑

学生选课时,系统可以按学院筛选课程
在后台管理中,管理员可以按学院查看学生情况

绑定关系:

每个学生必须选择一个所属学院

核心作用:

选课时:系统可以按学院筛选课程
管理时:可以按学院查看学生名单
统计时:可以分析各学院的学生数据

前端

Student.vue

1
2
3
4
5
6
7
8
9
10
11
<el-table-column label="所属学院" prop="collegeName"></el-table-column>

<el-form-item label="所属学院" prop="collegeId">
<el-select v-model="data.form.collegeId" placeholder="请选择学院" style="width: 100%">
<el-option v-for="item in data.collegeDate"
:key="item.id"
:label="item.name"
:value="item.id">
</el-option>
</el-select>
</el-form-item>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
const data = reactive({
// 教师信息弹窗对话框
formVisible: false,
// 教师信息表单数据
form: {
},
// 教师信息表格数据的数组,初始为空数组
tableData: [],
// 分页查询的页码
pageNum: 1,
// 分页查询的每页显示的记录数
pageSize: 5,
// 分页查询的总记录数,初始为0
total: 0,
// 教师姓名
name: null,
// 学院数据
collegeDate: [],
});

const loadCollege= () => {//查询所有学院信息
request.get('/college/selectAll').then(res => {//调用后端接口查询所有学院信息
if (res.code === '200') {//如果查询成功,将查询到的学院信息赋值给data.collegeDate
data.collegeDate = res.data
}else {//如果查询失败,提示用户
ElMessage.error(res.msg)
}
})
}

loadCollege()

StudentMapper.java

1
2
3
4
5
6
7
8
9
10
// 查询所有学生信息
@Select("select student.*, college.name as collegeName from student " +
"left join college on student.college_id = college.id")
List<Student> selectAll();

// 根据学生姓名查询学生信息,模糊查询
@Select("select student.*, college.name as collegeName from student " +
"left join college on student.college_id = college.id " +
"where name like concat('%',#{name},'%')")
List<Student> selectByName(String name);

学生个人资料中的关联信息

image-20250507222916974

学院

逻辑

前端操作:

学生在选课列表页面点击”取消选课”按钮
前端把要取消的选课记录ID传给后端接口

后端处理:

  1. 根据ID查询选课记录

  2. 删除这条选课记录

  3. 找到这门课程,把”已选人数”减1

SPerson.vue

1
2
3
4
5
6
7
8
9
10
11
12
13
14
const loadStudent = () => {
// 确保从localStorage获取用户信息并初始化data.user
data.user = JSON.parse(localStorage.getItem('system-user') || '{}')// 从缓存中获取用户信息

request.get('/student/selectById/' + data.user.id).then(res => {// 获取学生信息
if (res.code === '200') {
data.user = res.data// 存储到data.user中
localStorage.setItem('system-user', JSON.stringify(res.data))// 存储到缓存中
} else {
ElMessage.error(res.msg)
}
})
}
loadStudent()

StudentController.java

1
2
3
4
5
6
7
8
/**
* 根据id查询学生信息
*/
@GetMapping("/selectById/{id}")
public Result selectById(@PathVariable Integer id){
Student student = studentService.selectById(id);
return Result.success(student);
}

StudentService.java

1
2
3
public Student selectById(Integer id) {
return studentMapper.selectById(id);
}

StudentMapper.java

1
2
3
4
@Select("select student.*, college.name as collegeName from student " +
"left join college on student.college_id = college.id " +
" where student.id = #{id}")
Student selectById(Integer id);

学分

逻辑

学分计算规则:

学生每成功选一门课,系统自动把该课程的学分加到学生总学分上
学生退选课程时,系统自动扣除相应课程的学分

实时更新机制:

选课成功时:立即把课程学分加到学生总学分
取消选课时:立即从总学分中扣除相应学分
任何时候查看学生信息,显示的学分都是最新准确值

数据关联:

学生表有score字段记录总学分
课程表有score字段记录单门课程学分
选课操作时自动同步更新这两个字段

ChoiceService.java

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
/**
* 新增选课
*/
public void add(Course course) {
//判断课程是否已经选满
if(course.getNum().equals(course.getAlreadyNum())){//如果课程已经选满,就抛出异常
throw new CustomException("课程已经选满");
}
//判断这个学生这门课程是否已经选过
List<Choice> list = choiceMapper.selectByStudentIdAndCourseId(course.getStudentId(),course.getId());
if(CollectionUtil.isNotEmpty(list)){
throw new CustomException("你已经选过这门课程");//如果已经选过这门课程,就抛出异常
}
//往选课信息表中插入数据
Choice choice = new Choice();//创建一个choice对象
choice.setStudentId(course.getStudentId());//设置学生id
choice.setCourseId(course.getId());//设置课程id
choice.setTeacherId(course.getTeacherId());//设置教师id
choice.setName(course.getName());//设置课程名称
choiceMapper.insert(choice);//往选课信息表中插入数据
//该门课程的已选人数加1
course.setAlreadyNum(course.getAlreadyNum()+1);//已选人数加1
courseMapper.updateById(course);//更新课程信息
//该学生的学分增加
Student student = studentMapper.selectById(course.getStudentId());//查询学生信息
student.setScore(student.getScore()+course.getScore());//学分增加 学分=学分+课程学分
studentMapper.updateById(student);//更新学生信息
}

//根据id删除选课信息
public void deleteById(Integer id) {//传入一个id
Choice choice= choiceMapper.selectById(id);//查询选课信息
choiceMapper.deleteById(id);//删除选课信息
//该门课程的已选人数减1
Course course = courseMapper.selectById(choice.getCourseId());//查询课程信息
course.setAlreadyNum(course.getAlreadyNum()-1);//已选人数减1
courseMapper.updateById(course);//更新课程信息
//对应该学生的学分减少
Course dbCourse = courseMapper.selectById(choice.getCourseId());//查询课程信息
Student student = studentMapper.selectById(choice.getStudentId());//查询学生信息
student.setScore(student.getScore()-dbCourse.getScore());//学分减少 学分=学分-课程学分
studentMapper.updateById(student);//更新学生信息
}

终于做成了,然后把整体逻辑理一遍,放在01选课管理系统介绍