droolsoptaplannertimetable

Get index difference on Optaplanner - Drools


I'm working on a timetable scheduling problem with Drools. I have a rule that force the solver to always have a lecture on the previous timeslot (given a curriculum), at least since the first timeslot (index = 0) onwards. Example: if you have lectures on Monday from the timeslot 0 to 4 consecutively, you're ok; but if, for instance, you don't have a lecture on timeslot 2, then you have a -1 hard score.

// PeriodsWithoutLectures: All the periods must have consecutive lectures, at least since the 0 index timeslot onwards
rule "periodsWithoutLectures"
    when
        $curriculum : Curriculum()

        Lecture(curriculumList contains $curriculum,
            $day : day, $timeslotIndex : timeslotIndex, timeslotIndex > 0, period != null)
        not Lecture(curriculumList contains $curriculum,
            day == $day, timeslotIndex == ($timeslotIndex - 1))
    then
        scoreHolder.addHardConstraintMatch(kcontext, -1);
end

All of the above works, but what I need to do, is to know how many "missing lectures" I have. Giving the previous example, if I have a lecture on timeslot 0 and on timeslot 4, I'm missing 3 lectures in the middle (on timeslot 1, 2 and 3), so I need a -3 hard score (with my current approach, I'll get a -1 hard score).

Any help will be really useful, thanks!

UPDATE

This is what I have now:

rule "periodsWithoutLectures"
    when
        $curriculum : Curriculum()

        Lecture(curriculumList contains $curriculum,
            $day : day, $timeslotIndex1 : timeslotIndex, period != null)

        Lecture(curriculumList contains $curriculum,
            $day == day, $timeslotIndex2 : timeslotIndex, timeslotIndex > $timeslotIndex1 + 1, period != null)

        not Lecture(curriculumList contains $curriculum,
            day == $day, timeslotIndex > $timeslotIndex1 && < $timeslotIndex2)
    then
        scoreHolder.addHardConstraintMatch(kcontext, ($timeslotIndex2 - $timeslotIndex1) - 1);
end

Solution

  • Write a rule that does something like this:

    which then