You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何将OptaPlanner中规划实体的ConstraintStreams与关联问题事实属性结合?

解决课表中兼职教师课程紧凑性的约束方案

一、核心思路:通过分组聚合计算教师上课分布

你无需调整现有核心建模(Lesson作为规划实体、Teacher作为问题事实的设计是合理的),可以利用ConstraintStreams的groupBy功能,将同一教师的所有Lesson聚合起来,计算其上课天数、时段分布等全局属性,进而定义紧凑性约束。

二、具体实现步骤

1. 定义兼职教师判断逻辑

先实现判断教师是否属于需要紧凑安排的兼职人员(每周工作时长不足N小时):

// 示例:判断教师是否为需紧凑安排的兼职教师
private boolean isPartTimeTeacher(Teacher teacher, List<Lesson> lessons) {
    int totalWorkingHours = lessons.stream()
            .mapToInt(Lesson::getDurationHours)
            .sum();
    return totalWorkingHours < N; // N为业务设定的时长阈值
}

2. 用ConstraintStreams实现紧凑性约束

通过分组聚合同一教师的所有课程,计算实际上课天数与理想天数的差值,对分散情况进行惩罚:

Constraint teacherScheduleCompactness(ConstraintFactory constraintFactory) {
    return constraintFactory.from(Lesson.class)
            // 按教师分组,聚合该教师的全部课程
            .groupBy(Lesson::getTeacher, Collectors.toList())
            // 过滤出需要紧凑安排的兼职教师
            .filter((teacher, lessons) -> isPartTimeTeacher(teacher, lessons))
            // 计算实际上课天数与理想天数的差值
            .map((teacher, lessons) -> {
                Set<LocalDate> teachingDays = lessons.stream()
                        .map(lesson -> lesson.getTimeslot().getDate())
                        .collect(Collectors.toSet());
                int actualDays = teachingDays.size();
                // 根据时长阈值N确定理想天数:比如N<8小时理想1天,8≤N<16理想2天
                int idealDays = lessons.stream().mapToInt(Lesson::getDurationHours).sum() < 8 ? 1 : 2;
                // 实际天数超出理想天数的部分,作为惩罚依据
                return Math.max(0, actualDays - idealDays);
            })
            // 对每多出来的分散天数进行软惩罚(权重可根据业务优先级调整)
            .penalize("兼职教师课程分散", HardSoftScore.soft(100), excessDays -> excessDays);
}

3. 与常规约束结合

将该紧凑性约束和你现有的常规约束(如同一时间教师不能上两门课)一同添加到ConstraintProvider的约束定义方法中即可:

@Override
public Constraint[] defineConstraints(ConstraintFactory constraintFactory) {
    return new Constraint[] {
            // 常规约束:同一时间教师不可同时授课
            teacherConflict(constraintFactory),
            // 新增的紧凑性约束
            teacherScheduleCompactness(constraintFactory),
            // 其他业务约束...
    };
}

三、优化细节

  • 惩罚权重调整:如果紧凑性是优先级较高的软约束,可以调高soft(100)中的数值,提升其在得分计算中的权重。
  • 时段紧凑性进阶:若需要当天课程也尽量连排(避免中间空窗),可在分组后进一步计算单日时段的间隔,对空窗较多的情况额外增加惩罚。
  • 性能优化:若课表数据量较大,可在Lesson实体中预先缓存所属日期,避免每次流计算重复解析时段日期。

内容的提问来源于stack exchange,提问作者Daniel

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.26 14:50:20