Drools 规则引擎Word文档下载推荐.docx
《Drools 规则引擎Word文档下载推荐.docx》由会员分享,可在线阅读,更多相关《Drools 规则引擎Word文档下载推荐.docx(14页珍藏版)》请在冰豆网上搜索。
PackageBuilder
builder
=
new
PackageBuilder();
builder.addPackageFromDrl(
InputStreamReader(
getClass().getResourceAsStream(
"
package1.drl"
)
);
builder.addPackageFromXml(
package2.drl"
Package
pkg
builder.getPackage();
Figure2.1PackageBuilder
PackageBuilder是可以配置的,使用PackageBuilderConfiguration。
通常,你可以指定另一个parentClassLoader和用什么编译器(compiler),默认是EclipseJDT。
下面显示了如何指定JANINO编译器:
PackageBuilderConfiguration
conf
PackageBuilderConfiguration();
conf.setCompiler(
PackageBuilderConfiguration.JANINO
PackageBuilder(
Figure2.2.
PackageBuilderConfiguration
3.RuleBase:
Figure3.1.
RuleBase
一个RuleBase包含了多个将被使用的规则包(packagesofrules)。
一个RuleBase是可以序列化的,所以它可以被配置到JNDI或其他类似的服务。
通常,第一次使用时,一个RuleBase被创建并缓存。
RuleBase用RuleBaseFactory来实例化,默认返回一个ReteOORuleBase。
可以传入参数来指定采用ReteOO或Leaps。
然后,用addPackage方法加入Package实例。
你可以加入有相同命名空间(namespace)的多个Package。
RuleBase
ruleBase
RuleBaseFactory.newRuleBase();
ruleBase.addPackage(pkg);
Figure3.2.RuleBaseFactory
一个rulebaseinstance是线程安全的,所有你可以在你的应用中,让一个rulebaseinstance在多个线程中共享。
对于一个rulebase的最通常的操作是产生一个新的WorkingMemory。
这个rulebase保持着到它所产生的WorkingMemoryd的弱引用,所以在长时间运行的WorkingMemory中,如果rules发生改变,这些WorkingMemory可以即使的根据最新的rules进行更新,而不必重启WorkingMemory。
你也可以指定RuleBase不必保持一个弱引用,但是你要保证RuleBase不用更新。
ruleBase.newWorkingMemory();
//
maintains
a
weak
reference.
ruleBase.newWorkingMemory(
false
do
not
maintain
reference
任何时候,Package可以被加入或移除;
所有的改变都会被反映到现存的WorkingMemory中。
不要忘了调用fireAllRules()让Activations激发。
ruleBase.addPackage(
Add
package
instance
ruleBase.removePackage(
"
.sample"
remove
package,
and
all
its
parts,by
it'
s
namespace
ruleBase.removeRule(
my
rule"
specific
rule
from
anamespace
虽然有删除一个单独规则的方法,但是却没有加入一个单独规则的方法(要达到这个目的只有加入一个只有一条规则的package)。
4.WorkingMemory:
Figure4.1WorkingMemory
WorkingMemory是运行时规则引擎的主要类。
它保持了所有被asserted进WorkingMemory的数据的引用,直到取消(retracted)。
WorkingMemory是有状态对象。
它们的生命周期可长可短。
如果从一个短生命周期的角度来同一个引擎进行交互,意味着你可以使用RuleBase对象来为每个session产生一个新的WorkingMemory,然后在结束session后discard这个WorkingMemory(产生一个WorkingMemory是一个廉价的操作)。
另一种形式,就是在一个相当长的时间中(例如一个conversation),保持一个WorkingMemory,并且对于新的facts保持持续的更新。
当你希望dispose一个WorkingMemory的时候,最好的实践就是调用dispose()方法,此时RuleBase中对它的引用将会被移除(尽管这是一个弱引用)。
不管怎样最后它将会被当成垃圾收集掉。
术语WorkingMemoryActions代表了对WorkingMemory的assertions,retractions和modifications。
4.1Facts
Facts是从你的应用中,被assert进WorkingMemory中的对象(beans)。
Facts是规则可以访问的任意的java对象。
规则引擎中的facts并不是“clone”facts,它只是持有到你的应用中数据的引用。
Facts是你的应用数据。
String和其他没有getter和setter的类不是有效的Fact。
这样的类不能使用域约束(FieldConstraints),因为使用域约束要依靠JavaBean标准的getter和setter来同对象交互。
4.2Assertion
“Assertion”是将facts告诉WorkingMemory的动作,例如WorkingMemory.assertObject(yourObject)。
当你assert一个fact,它将被检查是否匹配规则。
这意味着所有的匹配工作将会在assert的过程中完成。
尽管如此,当你完成assertfacts之后,你还要调用“fireAllRules()”方法来执行规则。
当一个对象被assert后,会返回一个FactHandle。
这个FactHandle是一个代表在WorkingMemory中你的assertedObject的令牌(token)。
当你希望retract或者modify一个对象的时候,这个令牌让你用来同WorkingMemory进行交互。
Cheese
stilton
=
new
Cheese("
stilton"
);
FactHandle
stiltonHandle
workingMemory.assertObject(
WorkingMeomry有两种assertion模式:
Equality和Identity(默认是Identity)。
Identity模式下WorkingMemory使用一个IdentityHashMap来存储所有的assertedObjects。
这个模式下,当asserted的Object是同一个实例时,它返回同一个FactHandle。
Equality模式下WorkingMemory使用一个HashMap来存储所有的assertedObjects。
这个模式下,当asserted的Object相等时,它返回同一个FactHandle。
(WorkingMemory.assertObject(yourObjcet)只是进行assertion的一种regular方法,还存在有一种称为logicalassertion的动作)。
4.3Retraction
基本上就是assert的逆操作。
当你retract一个fact,WorkingMemory将不再跟踪那个fact。
任何被activated并依赖那个fact的规则将被取消。
完全有可能存在某条规则是依赖于一个fact的“不存在”(nonexistence)。
在这种情况下,retract一个fact将导致一条规则被激活。
对一个Fact进行Retraction,必须用assert时返回的那个FactHandle做为参数。
.
workingMemory.retractObject(
4.4Modification
当一个Fact被修改了,会通知规则引擎进行重新处理。
在规则引擎内部实际上是对旧的Fact进行retract,然后对新的Object再进行assert。
要使用modifyObject()方法来通知WorkingMemory,被改变的Object并不会自己通知规则引擎。
modifyObject()方法总是要把被修改的Object做为第二参数,这就允许你把一个不可变对象替换为另一个新对象。
stilton.setPrice(
100
workingMemory.modifyObject(
stiltonHandle,
4.5Globals
Global是一个能够被传进WorkingMemory但不需要assert的命名对象。
大多数这些对象被用来作为静态信息或服务。
这些服务被用在一条规则的RHS,或者可能是从规则引擎返回对象的一种方法。
List
list
ArrayList();
workingMemory.setGlobal("
list"
list);
setGlobal()方法传进去的命名对象必须同RuleBase中所定义的具有相同的类型(就是要同你的规则文件中用Global关键字所定义的类型相同),否则会抛出一个RuntimeException。
如果一条规则在你setGlobal之前调用了定义的Global,会抛出一个NullPointerException。
4.6PropertyChangeListener
如果你的fact对象是JavaBean,你可以为它们实现一个propertychangelistener,然后把它告诉规则引擎。
这意味着,当一个fact改变时,规则引擎将会自动知道,并进行响应的动作(你不需要调用modifyObject()方法来通知WorkingMemory)。
Proxylibraries将会帮助实现这一切。
要让PropertyChangeListener生效,还要将fact设置为动态(dynamic)模式,通过将true做为assertObject()方法的第二个参数来实现:
stilton,
true
//specifiesthat
this
is
dynamic
fact
然后要在JavaBean中加入一个PropertyChangeSupport实例,和两个方法:
addPropertyChangeListener()和removePropertyChangeListener()。
最后要在JavaBean的setter方法中通知PropertyChangeSupport所发生的变化。
示例代码如下:
private
final
PropertyChangeSupport
changes
PropertyChangeSupport(
this
public
void
addPropertyChangeListener(final
PropertyChangeListener
l)
{
this.changes.addPropertyChangeListener(
l
}
removePropertyChangeListener(final
this.changes.removePropertyChangeListener(
setState(final
String
newState)
oldState
this.state;
this.state
newState;
this.changes.firePropertyChange(
state"
oldState,
newState
5.Agenda:
Figure5.1.Agenda
Agenda是RETE的一个特点。
在一个WorkingMemoryAction发生时,可能会有多条规则发生完全匹配。
当一条规则完全匹配的时候,一个Activation就被创建(引用了这条规则和与其匹配的facts),然后放进Agenda中。
Agenda通过使用冲突解决策略(ConflictResolutionStrategy)来安排这些Activations的执行。
引擎工作在一个“2阶段”模式下:
1)
WorkingMemoryActions:
assert新的facts,修改存在的facts和retractfacts都是WorkingMemoryActions。
通过在应用程序中调用fireAllRules()方法,会使引擎转换到AgendaEvaluatioin阶段。
2)
AgendaEvaluation:
尝试选择一条规则进行激发(fire)。
如果规则没有找到就退出,否则它就尝试激发这条规则,然后转换到WorkingMemoryActions阶段,直到Agenda中为空。
这个过程一直重复,直到Agenda是空的,此时控制权就回到应用程序中。
。
当WorkingMemoryActions发生时,没有规则正在被激发。
下图说明了这个循环的过程:
Figure
5.2.
TwoPhaseExecution
5.1ConflictResultion
当有多条rules在agenda中,就需要解决冲突。
当激发一条规则时,会对WorkingMemory产生副作用。
规则引擎需要知道规则要以什么顺序来激发(例如,激发ruleA可能会引起ruleB被从agenda中移除。
)
Drools采取的冲突解决策略有2种,按照优先级排列如下:
Salience,LIFO(后进先出)。
最易懂的策略是“Salience”,即优先级,user可以为某个rule指定一个高一点的优先级(通过附给它一个比较大的数字)。
高Salience的rule将会被优先激发。
5.2AgendaGroups
AgendaGroups是划分Agenda中rules(其实是“activations”)的一种方法。
在任意一个时刻,只有一个group拥有“focus”,这意味着只有在那个group中的activations才是有效的。
AgendaGroups是在groupedrules之间创建一个“流”(flow)的简便的方法。
你可以在规则引擎中,或是用API来切换具有焦点的组。
如果你的规则有很明确的多“阶段”(phases)或多“序列”(sequences)的处理,可以考虑用AgendaGroups来达到这个目的。
每次调用setFocus()方法的时候,那个AgendaGroup就会被压入一个堆栈,当这个有焦点的组为空时,它就会被弹出,然后下一个组就会被执行。
一个AgendaGroup可以出现在堆栈的多个位置。
默认的AgendaGroup是“MAIN”,所有没有被指定AgendaGroup的Activations都被放到那个组中,这个组总是被放在堆栈的第一个组,并默认给予焦点。
5.3
AgendaFilters
Figure5.3.
AgendaFilter
Filter必须实现AgendaFilter接口,用来允许或禁止一个activation能够被激发。
Drools提供了下面几种方便的默认实现:
∙
RuleNameEndWithAgendaFilter
RuleNameEqualsAgendaFilter
RuleNameStartsWithAgendaFilter
要使用一个filter就要在调用fireAllRules()方法的时候指定它。
下面的例子将对所有名字以“Test”结尾的规则进行过滤:
workingMemory.fireAllRules(
RuleNameEndsWithAgendaFilter(
Test"
6.事件模型(EventModel)
Event包里提供了规则引擎的事件机制,包括规则激发,对象被asserted等等。
你可以使用事件机制来进行AOP编程。
有两种类型的EventListener:
WorkingMemoryEventListener和AgendaEventListener。
Figure6.1.
WorkingMemoryEventListener
Figure6.2
AgendaEventListener
对两个EventListener接口都提供了默认实现,但在方法中并没有做任何事。
你可以继承这两个默认实现来完成你自己的实现-DefaultAgendaEventListener和DefaultWorkingMemoryEventListener。
下面代码说明了如何扩展一个DefaultAgendaEventListner并把它加到WorkingMemory中,例子中只完成了afterActivationFired()方法:
workingMemory.addEventListener(
DefaultAgendaEventListener()
{
public
afterActivationFired(AfterActivationFiredEvent
event)
super.afterActivationFired(
event
System.out.println(