繁体   English   中英

OptaPlanner 自定义员工排班 - 约束提供程序中的 WeeklyHoursLimit 问题

[英]OptaPlanner Custom Employee Rostering - Issues with WeeklyHoursLimit in the Constraint Provider

我一直在关注员工排班示例来创建自定义员工排班服务。 我正在尝试实施每周工作时间限制。 但是,我无法达到每位员工每周最多工作 40 小时的预期限制。 我尝试复制 OptaPlanner 员工排班解决方案。 这是我想出的,但无论我尝试什么输入,解决方案都不会返回匹配项。

 Constraint weeklyHoursUpperLimit(ConstraintFactory constraintFactory) {
    return constraintFactory.from(Employee.class)
            .join(Schedule.class, equal(Function.identity(), Schedule::getEmployee))
            .groupBy((employee, schedule) -> employee,
                    ((employee, schedule) -> ZonedDateTime.parse(schedule.getTimeslot().getStart()).toLocalDate()
                            .with(TemporalAdjusters.previousOrSame(DayOfWeek.SUNDAY))),
                    sumDuration((employee, schedule) -> Duration.between(ZonedDateTime.parse(schedule.getTimeslot().getStart()),
                            ZonedDateTime.parse(schedule.getTimeslot().getEnd()))))
            .filter((practitioner, day, time) -> time.toHoursPart() > 40)
            .penalize("Practitioners cannot work more than 40 hours per week", HardMediumSoftScore.ONE_HARD);

解决方案是一个包含 Employee 和相应时间段的 Schedule 类型列表,它似乎与期望的行为不匹配。

使用以下输入:

{
    "employees": [
        {
            "id": "0458d419-da18-4d86-82de-31a2272f018a"
        }
    ],
    "timeslots": [
        {
            "start": "2021-05-24T00:00:00-04:00",
            "end": "2021-05-24T12:00:00-04:00",
            "slotId": 1
        },
        {
            "start": "2021-05-24T12:00:00-04:00",
            "end": "2021-05-25T00:00:00-04:00",
            "slotId": 7
        },
        {
            "start": "2021-05-25T12:00:00-04:00",
            "end": "2021-05-26T00:00:00-04:00",
            "slotId": 4
        },
        {
            "start": "2021-05-27T12:00:00-04:00",
            "end": "2021-05-28T00:00:00-04:00",
            "slotId": 5
        }
    ]
}

ScoreExplanation 表示:约束(从业者每周工作不能超过 40 小时)有 0 个匹配项。

应该说什么:约束(从业者每周工作不能超过 40 小时)有 1 个匹配项。

有了这个输入,唯一可能的解决方案必须匹配这个约束。 检测到其他约束并对其进行处罚,所以我想知道为什么这个约束从不返回任何匹配项。

我怀疑问题出在过滤器中: .filter((practitioner, day, time) -> time.toHoursPart() > 40)

Duration#toHoursPart()在将总小时数除以一天中的小时数后返回余数,介于 0 和 23 之间。过滤器可能应该使用Duration#toHours()代替。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM