Skip to end of metadata
Go to start of metadata

URule2技术交流QQ群及在线体验示例

在线体验示例:http://112.124.15.63:8084/ 为了不同用户操作互不影响,需要注册账号登录体验操作。

URule2技术交流QQ群:423339793

URule2规则引擎产品教学视频:https://pan.baidu.com/s/1oAeJeCM,密码:evsk

关于视频中对c及c1的引用

在本集视频最后的例子中,对于引用名的使用,引用名前忘记添加“!”符号,所以导致控制台输出时"c.名称"及"c1.名称"值为null,正确的写法是"!c.名称"及"!c1.名称"

       顾名思义,脚本式决策集就是通过脚本来定义决策集。在URule当中,脚本式决策集与向导式决策集是等价的,也就是说向导式决策集能实现的功能在脚本式决策集里都可以实现,反之亦然。在脚本式决策集里同样有普通规则、循环规则,同样可以对条件进行命名引用。

       URule中的脚本式决策集,采用URule自定义的一套脚本语法,关键字既可以使用英文也可以是中文,在一个普通规则或一个循环规则当中,我们可以使用纯英文关键字来定义,也可以全部使用纯中文关键字来定义,如果愿意,你也可以使用中英文混合的关键字来定义。因为支持中文关键字,使得URule的脚本式决策集更加适合国人编写,可读性也就更强,再配合URule中提供的脚本式决策集编辑器中提供的全功能代码提示功能,可大幅提高脚本式决策集的编写效率。

       打开URule控制台,在项目下的“决策集”节点右键,选择“添加脚本式决策集”菜单项,即可创建一个新的脚本式决策集文件,如下图所示:

       在这个编辑器当中,最上方同样也是工具栏,通过这个工具栏我们可以实现脚本文件的保存、导入常量、导入变量、导入参数库及导入动作库操作,与向导式规则文件不同之处在于,这里规则需要我们按URule提供的规则语法进行编写。

语法

       URule中的脚本的语法定义与解析采用的是ANTLR实现,在一个脚本式决策集当中,同样可以导入变量库、常量库、参数库以及动作库,同样可以编写普通规则和循环规则。对于一个完整的脚本规则文件,它的内容主要由三部分构成,分别是:导入资源库的头部分、规则定义部分以及函数定义部分。我们先来看看资源库导入的头部分。

库文件导入部分

       所谓的库文件导入部分,就是指在整个脚本规则文件的最顶部来定义导入哪些库文件,前面提到,通过最上方的工具栏,可以将我们规则当中需要用到的资源为导入进来。以导入变量库文件为例,在导入操作之前,需要我们首先将编辑光标定位于文件头部,然后点击最上方工具栏中“导入常量”按钮,在弹出窗口中选择目标资源库文件,确定后,就可以在当前脚本规则文件中加入要导入的资源库文件,如下图所示:

       导入其它类型的资源库操作也是一样,每条导入可以添加“;”结尾,也可以不加;在导入资源库文件时,如果我们选择当前资源库文件的某个具体版本,那么版本号就会出现在文件名的后方,如下图所示:

       可以看到版本号置于文件结尾处,与文件名之间以“:”分隔。

 

库文件导入定义位置

需要注意的是,导入库文件的定义信息,必须要置于整个脚本规则文件的顶部,具体的规则及函数定义必须位于导入资源库定义信息之下,否则就有语法错误。但对于变量库、参数库、常量库及动作库之间的顺序则是任意的。

       接下来我们来看看规则与函数定义,规则与函数他们之间的位置是任意的,只是保证它们位置导入资源库定义内容之下就行。我们先来看看规则定义。

规则定义

       在一个脚本式规则文件当中,可以添加零至多个普通规则或循环规则定义信息,其定义位置必须要在导入库文件的定义信息之下。一个标准的普通规则定义的结构如下。

       在一个普通规则当中,else部分如果没有动作可定义,那么是可以省略不写的,就像下面这样:

       看完普通规则后,我们再来看看循环规则定义,下面是一个标准的循环规则定义结构:

       对照向导式决策集里的循环规则定义,可以看到结构完全一致,唯一不同的是这里采用脚本方式实现。同样在脚本式循环规则的循环体中,如果没有“否则”部分,那么这里的“else”部分的定义就可以省略,这与普通规则一样。

规则属性

       无论是普通规则,还是循环规则,属性定义部分都是一样的,而且与向导式规则中普通规则和循环规则保持一致。如果不记得属性有哪些可以通过ALT+"/"键打开代码提示,选择需要的属性即可,多个属性之间可以用空格或","号分隔,具体属性中英文名及描述见4.决策集中关于规则属性部分介绍,如下图所示:

代码提示

在URule提供的脚本式决策集编辑器当中,通过使用ALT+"/"键就可以打开当前光标所在位置的代码提示功能,如果你在按ALT+"/"键时没出现代码提示菜单,则你的浏览器可能已占用了这个快捷键,我们必须要将这个快捷键开放出现,留给URule的脚本式决策集编辑器使用。

       属性赋值通过”=“实现,多个属性之间需要添加空格或回车,对于String类型的属性值需要添加双引号包裹,日期类型要采用“yyyy-MM-dd HH:mm:ss”格式来定义,布尔类型则直接输入true或false,如下图所示的属性:

条件定义部分

       对于一个普通规则,条件定义部分在if与then之间,对于循环规则,条件定义部分指的是循环体中在if与then之间的部分。在条件定义部分中我们可以添加具体的业务条件判断,与向导式规则类似,在编写脚本式规则条件时,单个条件也是由条件左边部分,比较操作符及条件右边部分。在条件左边部分,同样可以使用参数、变量及方法,当然也可以添加简单的加、减、乘、除,对于条件的比较操作符,我们可以通过ALT+"/"键打开代码提示来进行查看,如下图所示:

条件左边值

       条件左边值格式如下:

条件左值语法格式

变量/参数/方法 [+][/][*][/] 数字/字符串 [+][/][*][/] 数字/字符串...

       可以看到在定义条件左边值时,必须要以“变量/参数/方法”开头,且只能有一个变量/参数/方法,其后可跟一级或多级加、减、乘、除操作,但操作的对象必须是普通的数据或字符串,而不能再有“变量、参数或方法”等类型的值。同时在条件左值定义中,不能使用括号来实现加、减、乘、除运算优先级。下面是几个合法的条件左边值定义示例:

合法的条件左边值定义示例
员工.salary
员工.salary+10
员工.salary-10
员工.salary-10
员工.salary*10
员工.salary/10
员工.salary+10-5*2/3
MethodTest.判断用户名("张三")
MethodTest.判断用户名("张三")+12*12
参数.approve
参数.amount+10

       下面的这些例子就属于不合法的条件左值定义:

不合法的条件左值定义
不合法的原因
10以一个普通的数字开头是不合法的,条件左值要求必须以“变量/参数/方法”开头
"ok"以一个普通的字符串开头是不合法的,条件左值要求必须以“变量/参数/方法”开头
员工.salary+员工.level出现了两个变量,条件左值只能有一个“变量/参数/方法”
MethodTest.判断用户名("张三")+员工.salary出现了一个方法和一个变量,条件左值只能有一个“变量/参数/方法”
员工.salary+(10-5)*2/3出现了括号,在条件左值定义中,不能使用括号来实现加、减、乘、除运算优先级

条件右边值

         相比条件左边值,条件右边值的定义要灵活的多,除了可输入单个普通的数字、字符串、变量、参数、方法、常量外,也可以使用一级或多级加、减、乘、除操作连接复杂表达式,但一级或多级加、减、乘、除操作的右边对象同样可以是普通的数字、字符串、变量、参数、方法、常量,其语法格式如下:

 

条件右值语法

数字/字符串/变量/参数/方法/常量 [+][-][*][/] 数字/字符串/变量/参数/方法/常量 [+][-][*][/] 数字/字符串/变量/参数/方法/常量 ...

       在条件右边值当中,可以使用括号来实现加、减、乘、除运算优先级,依照条件右边值语法格式,上面条件左边值格式为不合法的示例,在条件右边值中都是合法的。在条件左值当中,我们可不以使用常量,但在条件右值当中就可以使用常量,下面是几个合法的条件右边值定义示例:

合法的条件右边值定义示例
10
20*0.08
20*0.08+30
10+20
$学历.大专
"ok"
true
false
员工.salary
员工.salary+10
员工.salary*10
员工.salary/10
参数.amount+10
参数.approve
员工.salary-10
员工.salary-10
员工.salary+10-5*2/3
MethodTest.判断用户名("张三")
员工.salary+10-5*2/3*(2+1.11)
MethodTest.判断用户名("张三")+12*12
员工.salary+员工.level+10
MethodTest.判断用户名("张三")+员工.salary
员工.salary+10-(员工.level-2.11*(2+2.1))

         因为条件右值当中可以添加括号来实现算术运行的优先级,所以下面的表达式就是合法的了:

         员工.salary+(10-5)*2/3

多条件组合

        在规则编写过程当中,如果有多个条件,那么可以采用“and”或“or”符号来对多个条件进行连接组合,同时对于组合的条件,还可以添加括号来实现组件条件计算的优先级,在未添加括号的多个组合条件之间,要使用相同连接符号,也就是说在未添加括号的多个组合条件之间,要么使用“and”,要么使用“or”。下面当前罗列了一些常用的组合条件示例:

组合条件
描述
员工.level==1 or 员工.level==2两条件只满足一个条件即可
员工.salary>1000 and 员工.salary<10000两条件必须同时满足

员工.salary>1000 and 员工.salary<10000 and (员工.level==1 or 员工.level==2 or

(员工.学历 == $学历.大专 and 员工.salary>员工.level*1.5 and 员工.dept.id=="D21"))

前两个条件满足,括号内前两个条件与最后那括号内条件必须要满足其一
员工.salary>1000 and 员工.salary<10000 and (员工.level==1 or 员工.level==2)前两个条件必须同时满足,同时后面两个条件必须要有一个满足
员工.学历 == $学历.大专 and 员工.salary>员工.level*1.5 and 员工.dept.id=="D21"表示三个条件必须同时满足

       通过上面的例子可以看到,通过“and”或“or”符号来对多个条件进行连接组合以及添加括号或多层嵌套括号可以实现非常复杂的条件组合,从而满足我们的业务需求。对于连接多个条件的“and”或“or”符号,在使用时还可以用“&&”或“||”来替换,熟悉Java的程序员一定很熟悉,“&&”或“||”在Java中表示的就是“并且”“或者”,除此之外,我们还可以直接使用“并且”“或者”的中文来连接多个条件,如下面的截图所示:


动作定义部分

       脚本式决策集中普通规则的的动作定义部分写在“then”与“end”之间或者是“else”与“end”之间,循环规则中除了循环体中可在上述两个地方添加动作外,还可以在"loopStart"与“if”之间或"loopEnd"与"end"之间添加动作,动作可有一个或多个,每个动作以“;”或回车结束。可执行的动作有三种类型,那就是为变量或参数赋值、执行方法、执行自定义函数以及控制台内容输出。我们首先来看看针对变量或参数的赋值操作。

赋值操作

        赋值操作的语法格式如下:

 

赋值动作语法

变量或参数 = 数字/字符串/变量/参数/方法/常量 [+][-][*][/] 数字/字符串/变量/参数/方法/常量 [+][-][*][/] 数字/字符串/变量/参数/方法/常量 ...

    可以看到,针对变量或参数的赋值,首先要写出具体的变量或参数名,然后是“=”符号,接下来在“=”右边是一个简单或复杂的赋值表达式。在这里赋值表达式与条件的右边值格式完全相同,所以这里不再赘述。

执行方法

       在做执行方法操作时,我们需要导入定义目标方法的动作库,一旦导入,我们通过ALT+"/"键代码提示中就可以看到当前文件中可用的方法,选择好一个方法后,如果这个方法中包含参数,那么我们还要根据在方法定义时指定的参数类型,为方法填充适当的参数,对于方法参数,它也支持类型条件右边值那种复杂的语法格式,执行方法的语法格式如下:

 

执行方法的语法格式

方法名([参数1,参数2...])

执行自定义函数

       所谓执行自定义函数是指执行在当前规则文件当中定义的自定义函数,关于自定义函数见后面内容描述,执行自定义函数的格式如下:

执行自定义函数格式

函数名([参数1,参数2...])

控制台内容输出

       在URule当中,内置了一个名为out的向控制台内容输出内容的函数,其语法格式如下:

控制台内容输出语法格式

out(数字/字符串/变量/参数/方法/常量 [+][-][*][/] 数字/字符串/变量/参数/方法/常量 [+][-][*][/] 数字/字符串/变量/参数/方法/常量 ... )

       从格式中可以看到,它以“out”开头,后面的括号中就是我们需要输出的内容,对于输出内容格式,与条件的右边值格式完全相同。

对中文的支持

       在规则编写当中,无论是普通规则还是循环规则,所有的关键字可以使用对应的中文来进行替代,具体见下表:

关键字
对应的中文关键字
rule规则
loopRule循环规则
loopTarget循环对象
loopStart开始前动作
loopEnd结束后动作
if如果
then那么
end结束
and并且
or或者
>大于
<小于
>=大于等于
<=小于等于
==等于
!=不等于
EndWith结束于
NotEndWith不结束于
StartWith开始于
NotStartWith不开始于
In在集合中
NotIn不在集合中
Match匹配
NotMatch不匹配
EqualsIgnoreCase忽略大小写等于
NotEqualsIgnoreCase忽略大小写不等于

       下表中三个规则定义在URULE中是等价的,都可以被识别:


    上面的截图中是一个用英文关键字编写的普通规则


    上面的截图中是一个用中文关键字编写的普通规则



       中英文关键字混合的普通规则与循环规则。

引用命名条件(此功能PRO版以及最新的开源版本都不再支持)

       在向导式决策集中,我们介绍了引用命名条件,在脚本式决策集中同样支持引用命名条件,在条件部分中,引用命名条件定义的语法如下:

引用命名条件语法

引用名:变量名(变量属性 比较操作符 具体值 [and/or (变量属性 比较操作符 具体值)]... )

       下面这些写法都是合法的:

引用命名条件定义示例
u:用户(年龄>50 同时 level<5)
user:用户(年龄>50 同时 (level<5 或者 婚否==false))
user:用户(年龄>50 同时 (level<5 或者 婚否==false)) and 会员.age>50
user:用户(年龄>50 同时 (level<5 或者 婚否==false)) and 会员.age>50 and emp:员工(薪水<10000 或者 age>50)

       可以看到,在引用命名条件时,在括号中定义具体属性的条件时,是不需要添加变量属性对应的分类的,否则就会产生错误。同时和向导式命名条件一样,在脚本当中,引用命名条件和普通条件可以混合在一起使用,较为复杂的引用命名条件可以通过括号实现计算的优先级。

       在条件部分中定义好可引用的命名条件后,接下来就可以在“那么”的动作部分使用这些引用对象,需要注意的是,无论是普通脚本式规则或循环规则的规则体中,只能在“那么”的动作部分使用这些引用对象,使用的方法比较简单,就是引用名+“.”+属性名,下图中是一个定义好的使用引用命名条件的示例:

       对于引用的名称,它可以是任意合法的变量名,但我们推荐使用纯英文来对其进行标识,如上图中的c中c1等。

动作部分引用名的使用

在脚本式决策集中,动作当中使用引用名,如上图中使用c或c1,必须要在引用名前添加“!”符号,否则将无法实现对引用名的使用,这点非常关键。

示例

       这里我们要把4.决策集中介绍的三个示例通过脚本式决策集实现以展示脚本式决策集用法。

示例一

       首先我们来看看第一个示例,其向导式决策集的截图如下所示:

       采用脚本式决策集来实现上面的两个规则,效果如下:

关于注释

在脚本式决策集中,可通过//来添加单行备注,多行备注用/..备注内容../实现

       通过“知识包”节点的仿真测试,对这个脚本式决策集进行打包测试,可以看到,其生成的Rete树与向导式的完全相同,同时仿真测试结果也与向导式完全相同。

示例二

 

       我们来看看向导式决策集中第二个例子,这是一个关于循环规则使用的示例,其内容如下图所示:

       将上述向导式循环规则用脚本方式实现,如下图所示:

       同样对这个脚本式的循环规则进行打包测试,可以得到与向导式完全相同的结果。

       如果需要在循环过程中进行中断,那么只需要添加一个“中断循环”的内置动作即可,如下图所示:

Labels
  • No labels