Использование CountableValueRange в правилах - PullRequest
0 голосов
/ 30 сентября 2019

В настоящее время я создаю приложение для планирования задач, совместно использующих некоторые ресурсы. Каждое задание может использовать определенный процент ресурса.

Что мне нужно проверить в правилах Drools, так это то, что каждый общий ресурс не используется более чем на 100% параллельными задачами.

Таким образом, код выглядит так:

@Data
public class Resource {
   @PlanningId
   private Integer id;

   private String label;
}
public class ResourceUsage {
   @PlanningId
   private Integer id;

   private Resource resource;

   private int usagePercent;

}

Объект для планирования

@Data
@PlanningEntity
public class TaskAssignment {
   @PlanningId
   private Integer id;

   @PlanningVariable(valueRangeProviderRefs = { "slotRange" })
   private Integer timeSlot;

   private int duration;
   private ResourceUsage resourceUsage;

   public Integer getEndingSlot() {
        return timeSlot + duration;
   }
}

И, наконец, решение

@Data
@PlanningSolution
public class PlanningSolution {
  @PlanningId
  private Integer id;

  @PlanningEntityCollectionProperty
  private List<TaskAssignment> tasks = new ArrayList<>();

  @ValueRangeProvider(id = "slotRange")
  public CountableValueRange<Integer> getSlotRange() {
        return ValueRangeFactory.createIntValueRange(0, 10_000);
  }

  @ProblemFactCollectionProperty
  private Set<Resource> resources = new TreeSet<>();
}

Установщики и получатели отсутствуют, поскольку я использую Lombok, чтобы избежать их записи.

ВВ прошлом я использовал класс для временных интервалов, и было легко написать правило для перебора коллекции временных интервалов, и я мог проверять глобальное использование каждого ресурса по временным интервалам и штрафовать, когда его использование превышало 100%.

Поскольку у меня были проблемы с использованием памяти, я решил превратить класс TimeSlot в CountableValueRange , но сейчас я не знаю, как создать правило, соответствующее каждому значению диапазона. выполнить тот же расчет, что и раньше.

Есть ли способ или мне нужно переключиться обратно на мой класс TimeSlot?

РЕДАКТИРОВАТЬ: Может ли переменная тени, содержащаяся в некотором объекте планирования тени, добиться цели?

1 Ответ

0 голосов
/ 08 октября 2019

Я наконец нашел способ написать правило, которое позволяет мне избегать повторения во временных интервалах. Идея состоит в том, чтобы посчитать использование в начале задания

rule "Maximum usage of a resource"
       when
             $r : Resource()
             $p : TaskAssignment($id1 : id, $ts : timeSlot != null,
                                 resourceUsage!.ressource==$r,
                                 $usage : resourceUsage!.usagePercent);
             accumulate(TaskAssignment(timeSlot != null, timeSlot <= $ts, 
                                      endingSlot > $ts, id != $id1, 
                                      resourceUsage!.ressource==$r, 
                                      $rate : resourceUsage!.usagePercent);
                                  $s:sum($rate);
                                  $s + $usage > 100) 
       then
             scoreHolder.addHardConstraintMatch(kcontext, 100-($s + $usage));         
end
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...