我在求解器配置中的本地搜索部分如下所示:
<acceptor>
<lateAcceptanceSize>400</lateAcceptanceSize>
<entityTabuSize>9</entityTabuSize>
</acceptor>
<forager>
<acceptedCountLimit>2000</acceptedCountLimit>
</forager>
并且一切正常但是当我将其更改为(我认为可能导致优化的因素):
<acceptor>
<lateAcceptanceSize>600</lateAcceptanceSize>
</acceptor>
<forager>
<acceptedCountLimit>4</acceptedCountLimit>
</forager>
解算器开始工作后我得到了异常
Score corruption: the solution's score (-20hard/-8medium/-4soft) is not the uncorruptedScore (-20hard/-8medium/-8soft)
什么可能导致这个问题? (它只是来自FULL_ASSERT模式的信息)
编辑:
可以将某些东西连接到规则:
// Boundary lessons have to be schedulead at the beginning/end in a day
rule "boundaryLesson"
when
$oddzial : Oddzial()
$boundaryLesson : Lesson(scheduled == true, containsOddzial($oddzial), base.lessonLimits.isBoundaryLesson == true, $base : base)
exists Lesson(scheduled == true, containsOddzial($oddzial), dayLessonNumber.day == $base.day, base.lessonNumberFrom < $base.lessonNumberFrom)
and exists Lesson(scheduled == true, containsOddzial($oddzial), dayLessonNumber.day == $base.day, base.lessonNumberTo > $base.lessonNumberTo)
then
scoreHolder.addHardConstraintMatch(kcontext, -1);
end
因为,有时我也会得到以下错误:
Score corruption: the workingScore (0hard/-2medium/0soft) is not the uncorruptedScore (-1hard/-2medium/0soft) after completedAction (8848-537:Tuesday-3 {com.pbz.plek.model.simple.DayLessonNr@5924af87 -> com.pbz.plek.model.simple.DayLessonNr@5924af87}):
The corrupted scoreDirector has no ConstraintMatch(s) which are in excess.
The corrupted scoreDirector has 1 ConstraintMatch(s) which are missing:
com.praca.mgr.cp.algorytm.solver/boundaryLesson/level0/[8854-537:Tuesday-2, com.krakfin.pbz.plek.model.simple.Oddzial@c9d4]=-1
Check your score constraints.
我知道增量分数计算是如何工作的,但我看不出这条规则会出现什么问题
答案 0 :(得分:1)
在这两种情况下,你都会有潜在的分数损坏,但只有第二种情况才会出现。为了提高生产可靠性,你肯定想要修复它。
请参阅有关“增量分数计算”的文档,以了解损坏分数。通常原因:
processWorkingSolutionDuringStep()
期间检测到。如果您使用Drools计算:
如果您使用增量分数计算:
<assertScoreDirectorFactor>
也可以使用简单的分数计算器。祝你好运。答案 1 :(得分:0)
总结一下:
每个分数都存在损坏分数的问题所以我离开了 只有硬约束规则部分,看起来像这样:
// ############################################# ############################### //硬约束 // ################################################# ############################
// two Lessons at the same time should be in another rooms.
rule "salaOccupancy"
when
$leftLesson : Lesson($id : base.numericId, scheduled == true, $sala : sala)
not Lesson(scheduled == true, timeCollision($leftLesson), sala == $sala, base.numericId < $id)
$rightLesson : Lesson(scheduled == true, timeCollision($leftLesson), sala == $sala, base.numericId > $id)
then
scoreHolder.addHardConstraintMatch(kcontext, -10);
end
// each oddzial and nauczyciel can't have two lessons at the same time
rule "przydzialCollision"
when
$przydzialConflict : PrzydzialConflict($leftPrzydzial : leftPrzydzial, $rightPrzydzial : rightPrzydzial)
$leftLesson : Lesson(scheduled == true, base.przydzial == $leftPrzydzial)
$rightLesson : Lesson(scheduled == true, base.przydzial == $rightPrzydzial, timeCollision($leftLesson), this != $leftLesson)
then
scoreHolder.addHardConstraintMatch(kcontext, -2 * $przydzialConflict.getConflictCount());
end
// sala's capacity shouldn't be exceeded
rule "salaCapacity"
when
$sala : Sala($capacity : ograniczenia.maxLiczbaUczniow.max)
$lesson : Lesson(scheduled == true, sala == $sala)
$limit : LessonStudentLimit(lesson == $lesson, numberOfStudents > $capacity)
then
scoreHolder.addHardConstraintMatch(kcontext, -2);
end
// cannot put lesson into not available time period in Sala or Przydzial
rule "availability"
when
Lesson( scheduled == true , dostepnaSala == false )
or Lesson( scheduled == true , dostepnyPrzydzial == false)
then
scoreHolder.addHardConstraintMatch(kcontext, -2);
end
// Oddzials cannot have gaps between classes during a day
rule "gaps"
when
$oddzial : Oddzial()
$dzien : DzienTygodnia()
$lessonList : ArrayList(LessonBlockCounter.calculateOddzialGaps($lessonList,TimetableSolution.maxLessonNr)>0) from collect (
Lesson(scheduled == true, containsOddzial($oddzial), dzienNrLekcji.dzien == $dzien)
)
then
scoreHolder.addHardConstraintMatch(kcontext, -5*LessonBlockCounter.calculateOddzialGaps($lessonList,TimetableSolution.maxLessonNr));
end
// If Przydzial has blocks distribution defined, only one lesson per day is allowed
rule "blocks"
when
$przydzial : Przydzial( ograniczenia.ograniczeniaBlokiLekcyjnePrzydzialu.czyTylkoJednaLekcjaNaDzien.isAktywne() == true )
$dzien : DzienTygodnia()
$lessonCount : Number( intValue > 1 ) from accumulate (
$lesson : Lesson(scheduled == true, base.przydzial == $przydzial,dzienNrLekcji.dzien == $dzien),
count($lesson)
)
then
scoreHolder.addHardConstraintMatch(kcontext, -2);
end
// Boundary lessons have to be schedulead at the beginning/end in a day
rule "boundaryLesson"
when
$oddzial : Oddzial()
$boundaryLesson : Lesson(scheduled == true, containsOddzial($oddzial), base.ograniczeniaLekcja.czyLekcjaGraniczna.aktywne == true, $base : base)
exists Lesson(scheduled == true, containsOddzial($oddzial), dzienNrLekcji.dzien == $base.dzien, base.lekcjaNrOd < $base.lekcjaNrOd)
and exists Lesson(scheduled == true, containsOddzial($oddzial), dzienNrLekcji.dzien == $base.dzien, base.lekcjaNrDo > $base.lekcjaNrDo)
then
scoreHolder.addHardConstraintMatch(kcontext, -1);
end
// Linked lessons have to take place at the same time
rule "linkedLesson"
when
$linkedLesson : Lesson(scheduled == true, base.ograniczeniaLekcja.lekcjePolaczone.empty == false, $dzienNrLekcji : dzienNrLekcji)
Lesson(scheduled == true, base.ograniczeniaLekcja.lekcjePolaczone contains $linkedLesson.base, dzienNrLekcji != $dzienNrLekcji)
then
scoreHolder.addHardConstraintMatch(kcontext, -5);
end
// Linked lessons have to take place at the same time
rule "scheduledLinkedLesson"
when
$linkedLesson : Lesson(scheduled == false, base.ograniczeniaLekcja.lekcjePolaczone.empty == false)
then
scoreHolder.addHardConstraintMatch(kcontext, -10*$linkedLesson.getBase().getCzasTrwania());
end
// Lessons have to be placed in the school time boundaries
rule "schoolTime"
when
$lesson : Lesson(scheduled == true, base.czasTrwania > 1 , base.lekcjaNrOd > TimetableSolution.maxLessonNr - base.czasTrwania)
then
scoreHolder.addHardConstraintMatch(kcontext, -5);
end
// Lessons have to be scheduled in one of the preferred sala
rule "assignedSalaPrzydzialu"
when
$lesson : Lesson( scheduled == true,
sala not memberOf base.przydzial.ograniczenia.perferowaneSale.preferowaneSale.saleList )
then
scoreHolder.addHardConstraintMatch(kcontext, -1);
end
// ############################################################################
// Medium constraints
// ############################################################################
//lesson have to have sala and day assigned, not assigned lessons are acceptable in overconstrained problem
rule "scheduledLesson"
when
$lesson : Lesson( scheduled == false )
then
scoreHolder.addMediumConstraintMatch(kcontext, -$lesson.getBase().getCzasTrwania());
end
运行算法后,我得到了异常:
2015-11-04 10:39:21,493 [http-8080-3] INFO org.optaplanner.core.impl.solver.DefaultSolver - Solving started: time spent (426), best score (uninitialized/-160hard/-165medium/0soft), environment mode (FULL_ASSERT), random (JDK with seed 0).
2015-11-04 10:39:23,969 [http-8080-3] INFO org.optaplanner.core.impl.constructionheuristic.DefaultConstructionHeuristicPhase - Construction Heuristic phase (0) ended: step total (165), time spent (2903), best score (-160hard/-165medium/0soft).
2015-11-04 10:39:24,615 [http-8080-3] ERROR org.apache.struts2.dispatcher.Dispatcher - Exception occurred during processing request: Score corruption: the solution's score (-123hard/-161medium/0soft) is not the uncorruptedScore (-126hard/-160medium/0soft).
java.lang.IllegalStateException: Score corruption: the solution's score (-123hard/-161medium/0soft) is not the uncorruptedScore (-126hard/-160medium/0soft).
at org.optaplanner.core.impl.score.director.AbstractScoreDirectorFactory.assertScoreFromScratch(AbstractScoreDirectorFactory.java:100)
at org.optaplanner.core.impl.solver.scope.DefaultSolverScope.assertScoreFromScratch(DefaultSolverScope.java:127)
at org.optaplanner.core.impl.solver.recaller.BestSolutionRecaller.processWorkingSolutionDuringStep(BestSolutionRecaller.java:107)
...
在研究问题后,我非常确定它与增量分数计算和drl文件有关。我认为该问题会导致“间隙”规则,因为“calulateOddzialGaps”方法会检查收集的$ lessonList的日期和课程编号,但在评论此规则问题后仍然存在。任何其他规则都不会在java方法中的WHEN部分使用课程(planningEntity)。有什么不对?我没有任何其他想法......