как получить доступ к карте пользовательских объектов в drools

1

У меня есть файл правил Drools, к которому я отправляю карту, заполненную пользовательскими объектами (NodeElement), map - это глобальная переменная, потому что к ней должны быть доступны все правила, есть еще одна ошибка глобальной переменной, которая заполняется, когда правило выходит из строя. Я использовал eval и смог успешно его выполнить. После некоторых исследований выяснилось, что у eval есть некоторые проблемы с производительностью?

Мои вопросы...

1) проблемы с производительностью незначительны?

2) использует eval хорошую практику?

3) если мне придется переписать эти правила? что это лучший способ сделать это?

import java.util.Map;
import com.infodev.pojo.NodeElement;
import com.main.Errors;
import com.validation.DateValidation;

global java.util.Map map;
global com.main.Errors errors;


rule "Fixed / Floating ccy rule"

    when
        eval(!((NodeElement)map.get("FixedCurrency")).getValue().equals(((NodeElement)map.get("FloatingCurrency")).getValue()))
    then 
        errors.addError( "Currency", "Fixed currency should be same as Floating currency" );
end

rule "Payment / Settlement date rule"

    when
        eval(!(DateValidation.paymentDateValidation(((NodeElement)map.get("tradeDate")).getValue(),((NodeElement)map.get("paymentDate")).getValue())))

    then 
        errors.addError(map.get("paymentDate").toString(), "Payment date should be after trade date" );

end

И карта:

Map<String, NodeElement> map = new HashMap<String, NodeElement>();
    map.put("FixedCurrency", new NodeElement("FixedCurrency", "USD"));
    map.put("FloatingCurrency", new NodeElement("FloatingCurrency", "UD"));
    map.put("tradeDate", new NodeElement("tradeDate", "2012-01-22"));
    map.put("paymentDate",new NodeElement("paymentDate", "2012-01-2"));
Теги:
drools
rule-engine

2 ответа

1
Лучший ответ

Учитывая, что NodeElement может быть идентифицирован с использованием той же Строки, которую вы используете в качестве ключа вашей Карты, почему бы вам не вставлять NodeElements в сеанс? Поступая таким образом, вы можете переписать свои правила следующим образом:

rule "Fixed / Floating ccy rule"
when
    $n1: NodeElement( id == "FixedCurrency")
    $n2: NodeElement( id == "FloatingCurrency", value != $n1.value)
then
    errors.addError( "Currency", "Fixed currency should be same as Floating currency" );
end

rule "Payment / Settlement date rule"
when
    $n1: NodeElement( id == "tradeDate")
    $n2: NodeElement( id == "paymentDate", value != $n1.value)
    eval(!(DateValidation.paymentDateValidation($n1.value, $n2.value)))
then
    errors.addError($n2.value.toString(), "Payment date should be after trade date" );
end

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

Надеюсь, поможет,

  • 1
    Почему бы не пройти весь путь и использовать FixedCurrency , TradeDate и т. Д. В качестве имен типов. Это действительно сделает его читабельным ;-)
  • 0
    Спасибо, это работает. Но просто спрашиваю, есть ли лучший способ сделать это? это может быть достигнуто еще более эффективно?
0

У вас нет правил, у вас есть инструкции (замаскированные под правила), касающиеся значений в объекте Map и другом статическом объекте. (Почему бы вам не запустить эти проверки после добавления на карту?)

Нет никакого eval я могу видеть в ваших правилах.

Если вам нужен eval, вам нужно использовать eval, если вы можете избежать этого, избегайте его.

  • 0
    извините, если это на самом деле Eval. и не уверен, что вы подразумеваете, когда вы говорите, что проверяет после добавления к карте, что означает использование if else вместо самопроизвольного сноса? ... приведенные выше правила могут быть простыми, n может быть решена с помощью if-else, но мои действительные правила будут сложными , Можете ли вы указать мне правильное направление, как это можно сделать без использования eval?
  • 0
    Вы не обращаетесь к каким-либо фактам в рабочей памяти в этих «правилах», поэтому то, что вы кодировали, - это просто оператор if. Да, вы можете запускать эти проверки как операторы Java if в коде Java, сразу после этих map.put(...) . - Как они написаны сейчас, вы должны использовать eval . Если они будут более сложными, они будут просто более сложными, если заявления под видом правил. И если все они похожи на это, просто получая доступ к нескольким статическим объектам, вы упускаете весь смысл системы производственных правил и можете придерживаться Java.
Показать ещё 3 комментария

Ещё вопросы

Сообщество Overcoder
Наверх
Меню