Алгоритм проверки состояния таблицы решений Drools

У меня есть вопрос о том, как оцениваются условия для таблиц решений Drools. Я думал, что условия оцениваются слева направо, и если самый левый столбец, который он проверял на заданное правило, был ложным, он не проверял остальные условия.

Одной из причин, по которой это важно для меня, является концепция размещения условий, которые сужают область действия, как можно дальше влево. Это означало бы, что объекты будут удалены раньше, чем большинство объектов, сначала удовлетворяющих широкому условию и продолжающих проверять дополнительные условия.

Однако это не то поведение, которое я наблюдал в модульном тесте, о котором я расскажу ниже.

Этот пример прост и не предназначен для демонстрации раннего сужения области действия.

|------------------|-------------------|
|Condition         |Condition          |
|------------------|-------------------|
|myObject          |myObject           |
|------------------|-------------------|
|isNameEq("$param")|isValueEq("$param")|
|------------------|-------------------|
|A                 |1                  |
|A                 |2                  |
|A                 |3                  |
|A                 |4                  |
|A                 |5                  |
|B                 |4                  |
|B                 |5                  |
|B                 |6                  |
|B                 |7                  |
|------------------|-------------------|

В этом примере isNameEq и isValueEq являются функциями из java-объекта myObject. Пожалуйста, игнорируйте любую небольшую ошибку Drools/отсутствие объявленного импорта, так как я знаю, что мой тест работает нормально, и эта иллюстрация является приблизительным, чтобы передать сценарий.

Две функции включают простую регистрацию, чтобы показать, когда они вызываются. Для объекта с именем = A и значением = 3 я ожидал бы, что функция isValueEq никогда не будет вызываться для правил с B в столбце имени (самый левый), потому что объект не соответствует этому условию.

Однако в журнале указано, что вызовы функций выполнялись в следующем порядке:

  1. isNameEq(A)
  2. isNameEq(B)
  3. isValueEq(1)
  4. isValueEq(2)
  5. isValueEq(3)
  6. isValueEq(4)
  7. isValueEq(5)
  8. isValueEq(6)
  9. isValueEq(7)

Это звучит правильно? Я просто ошибся в своем предположении? Является ли это частью алгоритма rete и кэширования оценок (узлов?), поскольку он не вызывал isValueEq для (B, 4), (B, 5)?

Спасибо всем, кто может пролить свет на это для меня!


person user3481923    schedule 31.03.2014    source источник


Ответы (1)


Каждая строка вашей электронной таблицы преобразуется в одно правило, например. ряд номер 1:

rule "whatever 1"
when
    MyObject( isNameEq("A"), isValueEq("1") )
then

и еще один с «А» и «2», и так далее. Каждый вставленный факт оценивается по этим правилам один за другим.

Преимущество алгоритма (Rete или что-то еще) может не проявиться, когда функции скрывают доступ к фактическим данным. Вы можете попробовать простые ограничения (имя == "A", значение == "1") и зарегистрировать доступ путем модификации геттера; это не повлияет на способ построения оценочной сети.

person laune    schedule 01.04.2014