Drools开源业务规则引擎(二)- Drools规则语言(DRL)


文章目录

    • 1.DRL文件的组成:
    • 2.package
    • 3.import
    • 4.function
    • 5.query
    • 6.declare
    • 7.global
    • 8.rule
      • 8.1.规则属性
      • 8.2.LHS
        • 8.2.1.语法格式
        • 8.2.2.运算符优先级
        • 8.2.3.特殊的运算符
          • 1.`matches`, `not matches`
          • 2.`contains`, `not contains`
          • 3.`memberOf`, `not memberOf`
          • 4.`in`, `notin`
          • 5.`soundslike`
          • 6.`str`
          • 7.`from`
      • 8.3.RHS
        • 8.3.1.`set`
        • 8.3.2.`modify`
        • 8.3.3.`update`
        • 8.3.4.`insert`
        • 8.3.5.`delete`
        • 8.3.6.`drools.halt()`


1.DRL文件的组成:

在官方文档中(链接地址 https://docs.drools.org/7.74.1.Final/drools-docs/html_single/index.html#_droolslanguagereferencechapter),DRL的组成如下:

packageimportfunction  // Optionalquery  // Optionaldeclare   // Optionalglobal   // Optionalrule "rule name"// Attributeswhen// Conditionsthen// Actions
endrule "rule2 name"...

以上内容,只是梳理了DRL文件中组成的元素及其顺序(顺序非强制性要求,这是这样便于内容阅读)。

2.package

类似于 Java 中的 package,声明规则的唯一命名空间(包)。包必须有一个名称空间,并使用包名称的标准 Java 约定进行声明;即没有空格,这与允许空格的规则名称不同。根据元素的顺序,它们可以以任何顺序出现在规则文件中,但package语句除外,它必须位于文件的顶部。在任何情况下,分号都是可选的。

任何规则属性(见“规则属性”一节)也可以在包级别编写,取代该属性的默认值。修改后的默认值仍可能被规则中的属性设置所替换。

示例

// 带分号
package com.test;
// 不带分号
package com.test

3.import

类似于 Java 中的 import。DRL文件中在规则中需要导入使用的对象的完全限定路径和类型名称。Drools引擎自动从与DRL包同名的Java包和Java.lang包中导入类。

示例

// 不需要导入,已自动导入
// import java.lang.String;import com.a.b.DroolsObject;

4.function

类似于 Java 中的 method。可以将重复代码或者逻辑性代码封装成一个函数,或者将工具/辅助类中的静态方法导入为函数,然后在规则LHS/RHS部分中按名称使用该函数。

示例

// 导入静态方法/函数
import static org.example.applicant.MyFunctions.hello;// 函数1
function boolean ageJudge(Integer i){if (i > 10){return true;} else {return false;}
}// 使用函数
rule "age"
enabled true
wheneval(ageJudge(10));
then
end

5.query

查询在工作内存中相关的事实对象。查询的名称对于 KieBase 是全局的,因此对于该项目中的所有其他规则的查询必须是唯一的。ksession.getQueryResults("name") 获取查询结果,其中“name”是查询名称。

示例

package drools.drl// 导入输入类型
import com.ahao.project.input.UserIn;
global com.ahao.project.output.UserOut output;query "age>10"$in:UserIn(age > 10)
end

获取结果

QueryResults queryResults = kieSession.getQueryResults("age>10");
Iterator<QueryResultsRow> iterator = queryResults.iterator();
while (iterator.hasNext()) {QueryResultsRow next = iterator.next();log.info("查询结果:{}",next.get("$in"));
}// [main] INFO DroolsTest2 - 查询结果:UserIn(age=35)
// [main] INFO DroolsTest2 - 查询结果:UserIn(age=45)

6.declare

声明类型。用于在DRL声明一个新的类型。

示例

package drools.drlimport com.ahao.project.input.UserIn// 声明一个Person类型
declare Personname:Stringage:Integer
endrule "age"
enabled true
when$in:UserIn(age > 10)
thenPerson person = new Person();person.setAge($in.getAge());person.setName("命中规则");System.out.println(person);
end

结果
在这里插入图片描述

7.global

全局变量。DRL文件中的全局变量通常为规则提供数据或服务,如在then中使用的应用程序服务(service),并从规则返回数据。

示例

// 全局变量的定义
global com.ahao.project.output.UserOut output;
// 可以有多个
// global com.ahao.project.output.UserOut output222;

注意:

执行规则时,需要先设置全局变量对象

kieSession.setGlobal("output", output);
// 然后再 kieSession.fireAllRules()

8.rule

rule语法结构如下图

rule

8.1.规则属性

属性默认值描述
salience0规则优先级。在同一个 activation-group 中,具有较高优先级(值越大)的规则优先执行
示例: salience 10
enabledtrue是否启用该规则
示例: enabled true
date-effectivenull只有当前日期时间在 date-effective 属性之时,才能激活该规则
示例: date-effective "4-Sep-2018"
date-expiresnull只有当前日期时间在 date-expires 属性之时,才能激活该规则
示例: date-expires "4-Oct-2018"
no-loopfalse是否可循环。某些情况下(update函数等),规则可以被再次激活
示例: no-loop true
agenda-groupdefault议程组。对议程进行分区,以提供对规则组的更多执行控制。只有获得焦点的议程组中的规则才能被激活。
示例: agenda-group "GroupName"
activation-groupnull激活组。一个激活组只能激活一个规则,即使其他规则体的LHS部分仍然为true也不会再被执行。
示例: activation-group "GroupName"
durationnull以毫秒为单位的持续时间。如果规则条件当前满足,则在该持续时间之后可以激活规则。
示例: duration 10000
timernull调度器。“时间间隔”或“cron”计时器定义
示例: timer ( cron:* 0/15 * * * ? ) (every 15 minutes)
calendarnull用于调度规则的 Quartz calendar
示例: calendars "* * 0-7,18-23 ? * *" (exclude non-business hours)
auto-focusfalse自动获取焦点,仅适用于议程组内的规则。选择该选项后,下次激活规则时,会自动将焦点指定给规则所分配的议程组:
示例:auto-focus true
lock-on-activefalse仅适用于规则流组或议程组内的规则。选择该选项后,下次规则的规则流组变为活动状态或规则的议程组收到焦点时,在规则流组不再活动或议程组失去焦点之前,无法再次激活规则。是no-loop属性的更强版本。
示例: lock-on-active true
ruleflow-groupnull规则流组。只有被关联的规则流激活这个组时,规则才能激活
示例: ruleflow-group "GroupName"
dialectmvel用来定义规则中要使用的语言类型
示例: dialect "java"

8.2.LHS

规则的when部分(也称为Left Hand Side(LHS))包含执行操作必须满足的条件。

8.2.1.语法格式

格式

// 格式如下(对象名称前的 $ 非必需的)
when$对象名称:事实对象的全限定类名(字段约束)// 如果已经import了事实对象的全限定类名
when$对象名称:事实对象的类名(字段约束)  

示例

// 示例1
when$p:com.test.Person(age > 10 || name == "jack")// 示例2
import com.test.Person;
whenp:Person(age > 10 || name == "jack")
8.2.2.运算符优先级
操作类型符号Notes
嵌套或(null-safe)属性访问., .(), !.不是标准的Java语义
List 或者 Map 访问[]不是标准的Java语义
约束绑定(类型绑定):不是标准的Java语义
乘积*, /,%
加减+, -
位运算>>, >>>, <<
关系型<, <=, >, >=, instanceof
等于== !=使用equals()!equals()语义,非标准Java samenot same语义
非短路 AND&
非短路异运算^
非短路包含 OR``
逻辑运算 AND&&
逻辑运算 OR`
三元运算符? :
逗号分隔 AND,不是标准的Java语义

运算符==使用null-safe equals()语义,而不是通常的equals语义。例如,Person(firstName=="John") 类似于 java.util。Objects.equals(person.getFirstName(),“John”),并且由于"John"不为null,所以该模式也类似于"John".equals(person.get-FirstName)

以上运算符都基本上类似java中的运算符。接下会介绍一些特殊的运算符。

8.2.3.特殊的运算符
1.matches, not matches

判断与指定的Java正则表达式匹配或不匹配。

示例

Person( country matches "(USA)?\\S*UK" )
2.contains, not contains

数组或集合字段是否包含指定值。可以使用这些运算符来代替String.contains()和!String.contents()。

示例

// 姓名包含王
Person( name contains "王" )
// 假设一个人有多个手机号,phones:List<String>
// 手机号不包含12345678901
Person( phones not contains "12345678901" )
3.memberOf, not memberOf

是否为数组或集合的成员。

示例

// 手机号不包含12345678901
Person( "12345678901" not memberOf phones)
4.in, notin

指定约束中要匹配的多个可能值(复合值限制)。

示例

// 名称为 jack 或者 mary
Person( name in ("jack","mary"))
5.soundslike

验证单词是否具有与给定值几乎相同的发音(英语发音)。

示例

// firstName "Jon" or "John":
Person( firstName soundslike "John" )
6.str

验证字符串字段是以指定值开始,以指定值结束,或者字符串的长度。

示例

// 消息的以"R1"开始
Message( msg str[startsWith] "R1" )// 消息的以"R2"结尾
Message( msg str[endsWith] "R2" )// 消息的长度为17
Message( msg str[length] 17 )
7.from

获取数据源。

示例

// 从模式绑定(变量)中获取数据源
rule "rule1"
whenPerson( $personAddress : address )Address( zipcode == "11110" ) from $personAddress
then
end// 从图形符号中获取数据源
rule "rule1"
when$p : Person()$a : Address( zipcode == "23920W" ) from $p.address
then
end// 从迭代器中获取数据源
rule "rule1"
when$order : Order()$item  : OrderItem( value > 100 ) from $order.items
then
end

8.3.RHS

规则的then部分(也称为 Right Hand Side(RHS))。当满足规则的when部分时要执行的操作。操作的主要目的是在Drools引擎的工作内存中插入、删除或修改数据。有效的规则操作是小的、声明性的和可读的。如果需要在规则操作中使用命令式或条件式代码,请将规则划分为多个更小、更具声明性的规则。

8.3.1.set

赋值。

示例

$person.setName("jack");
8.3.2.modify

针对某个事实进行修改,并将更改通知Drools引擎。

语法

modify ( <fact-expression> ) {<expression>,<expression>,...
}

示例

modify( Person ) {setAge( 100 ),setName ( "nick" )
}
8.3.3.update

指定要更新的字段和整个相关事实,并将更改通知Drools引擎。

语法

update ( <object, <handle> )
update ( <object> ) 

示例

person.setAge( 100 );
update( person );
8.3.4.insert

将一个新的事实插入Drools引擎的工作内存中。

语法

insert( new <object> );

示例

insert( new Person() );
8.3.5.delete

从Drools引擎中删除对象。

语法

delete( <object> );

示例

delete( person );
8.3.6.drools.halt()

终止规则执行。

示例

rule "end_rule"
enabled true
when
thendrools.halt();
end

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/42693.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Powershell 获取电脑保存的所有wifi密码

一. 知识点 netsh wlan show profiles 用于显示计算机上已保存的无线网络配置文件 Measure-Object 用于统计数量 [PSCustomObject]{ } 用于创建Powershell对象 [math]::Round 四舍五入 Write-Progress 显示进度条 二. 代码 只能获取中文Windows操作系统的wifi密码如果想获取…

护网在即,助力安服仔漏洞扫描~

整合了个漏扫系统&#xff0c;安服仔必备~ 使用场景 网前布防&#xff0c;漏洞扫描&#xff0c;资产梳理 使用方法&#xff1a; 启动虚拟机后运行命令&#xff1a; ./StartSystemScript.sh 输入密码attack 启动完成后浏览器打开网站&#xff1a; http://IP:5000 相关账户…

02-android studio实现下拉列表+单选框+年月日功能

一、下拉列表功能 1.效果图 2.实现过程 1&#xff09;添加组件 <LinearLayoutandroid:layout_width"match_parent"android:layout_height"wrap_content"android:layout_marginLeft"20dp"android:layout_marginRight"20dp"android…

运维系列.Nginx中使用HTTP压缩功能

运维专题 Nginx中使用HTTP压缩功能 - 文章信息 - Author: 李俊才 (jcLee95) Visit me at CSDN: https://jclee95.blog.csdn.netMy WebSite&#xff1a;http://thispage.tech/Email: 291148484163.com. Shenzhen ChinaAddress of this article:https://blog.csdn.net/qq_28550…

【刷题汇总--字符串中找出连续最长的数字串、岛屿数量、拼三角】

C日常刷题积累 今日刷题汇总 - day0071、字符串中找出连续最长的数字串1.1、题目1.2、思路1.3、程序实现 -- 比较1.4、程序实现 -- 双指针 2、岛屿数量2.1、题目2.2、思路2.3、程序实现 - dfs 3、拼三角3.1、题目3.2、思路3.3、程序实现 -- 蛮力法3.4、程序实现 -- 巧解(单调性…

pwm 呼吸灯(如果灯一直亮或者一直灭)

&#xff08;这个文章收藏在我的csdn keil文件夹下面&#xff09; 如果这样设置预分频和计数周期&#xff0c;那么算出来的pwm频率如下 人眼看起来就只能是一直亮或者灭&#xff0c;因为pwm的频率太高了&#xff0c;但是必须是频率够高&#xff0c;才能实现呼吸灯的缓慢亮缓慢…

SPL-404:如何彻底改变Solana上的NFT与DeFi

在不断发展的数字资产领域中&#xff0c;非同质化Token&#xff08;NFT&#xff09;已成为一股革命性力量&#xff0c;彻底改变了我们对数字所有权的看法和互动方式。从艺术和收藏品到游戏和虚拟房地产&#xff0c;NFT吸引了创作者、投资者和爱好者的想象力。 本指南将带您进入…

MyBatisPlus-分页插件的基本使用

目录 配置插件 使用分页API 配置插件 首先&#xff0c;要在配置类中注册MyBatisPlus的核心插件&#xff0c;同时添加分页插件。&#xff08;可以放到config软件包下&#xff09; 可以看到&#xff0c;我们定义了一个配置类&#xff0c;在配置类里声明了一个Bean,这个Bean的名…

排序 -- 计数排序以及对排序的总结

到了这篇文章就说明常见的排序我们就快要讲完了&#xff0c;那这篇文章我们就讲一下非比较排序--计数排序。 一、非比较排序 1.基本思想 计数排序又称为鸽巢原理&#xff0c;是对哈希直接定址法的变形应用。 操作步骤&#xff1a; 统计相同元素出现次数 根据统计的结果将序列…

昇思25天学习打卡营第14天|基于MindNLP的文本解码原理

基于MindNLP的文本解码原理 文本解码 文本解码是自然语言处理中的一个关键步骤,特别是在任务如机器翻译、文本摘要、自动回复生成等领域。解码过程涉及将编码器(如语言模型、翻译模型等)的输出转换为可读的文本序列。以下是一些常见的文本解码方法和原理: 1. 自回归解码:…

打造属于你的私人云盘:在 OrangePi AIpro 上搭建个人云盘

随着数字化时代的到来&#xff0c;数据的存储和管理变得愈发重要。相比于公共云存储服务&#xff0c;搭建一个属于自己的个人云盘不仅能够更好地保护隐私&#xff0c;还可以更灵活地管理数据。 近期刚好收到了一个 香橙派 AIpro 的开发板&#xff0c;借此机会用来搭建一个属于…

美股交易相关知识点 持续完善中

美股交易时间 美东时间&#xff1a;除了凌晨 03:50 ~ 04:00 这10分钟时间不可交易以外&#xff0c;其他时间都是可以交易的。 如果是在香港或者北京时间下交易要区分两种: 美东夏令时&#xff1a;除了下午 15:50 ~ 16:00 这10分钟时间不可交易以外&#xff0c;其他时间都是可…

法国工程师IMT联盟 密码学及其应用 2022年期末考试

1 密码学 1.1 问题1 对称加密&#xff08;密钥加密) 1.1.1 问题 对称密钥la cryptographie symtrique和公开密钥有哪些优缺点&#xff1f; 1.1.1.1 对称加密&#xff08;密钥加密)的优缺点 1.1.1.1.1 优点 加解密速度快encrypt and decrypt&#xff1a;对称加密算法通常基于…

【vue组件库搭建06】组件库构建及npm发包

一、格式化目录结构 根据以下图片搭建组件库目录 index.js作为入口文件&#xff0c;将所有组件引入&#xff0c;并注册组件名称 import { EButton } from "./Button"; export * from "./Button"; import { ECard } from "./Card"; export * fr…

一、MyBatis

一、MyBatis 1、MyBatis简介 1.1、MyBatis历史 MyBatis最初是Apache的一个开源项目iBatis, 2010年6月这个项目由Apache Software Foundation迁移到了Google Code。随着开发团队转投Google Code旗下&#xff0c; iBatis3.x正式更名为MyBatis。代码于2013年11月迁移到Github。…

计算机网络之无线局域网

1.无线局域网工作方式 工作方式&#xff1a;每台PC机上有一个无线收发机&#xff08;无线网卡&#xff09;&#xff0c; 它能够向网络上的其他PC机发送和接受无线电信号。 与有线以太网相似&#xff0c;无线局域网也是打包方式发送数据的。每块网卡都有一个永久的、唯一的ID号…

Unity2D - 基本战斗系统(Battle System Design)

1. 攻击逻辑 在Entity中初始化两个变量&#xff0c;因为在每个角色几乎都拥有攻击状态。这两个变量分别是transform类&#xff0c;接收一个坐标和一个半径画一个圆作为攻击的判定范围 public Transform attackCheck; public float attackCheckRadius; 为了可视化攻击范围&am…

基于ROS的智能网联车远程交互软件,全UI无需记忆指令,剑指核心原理。

基于ROS的智能网联车远程交互软件&#xff0c;全UI无需记忆指令&#xff0c;剑指核心原理。 服务于中汽恒泰&#xff0c;伟大的项目&#xff0c;希望看官点赞&#xff0c;谢谢~~ 进程&#xff08;节点&#xff09;列表化&#xff0c;参数面板化&#xff0c;实现快速机器人配置…

Linux--V4L2摄像头驱动框架及UVC浅析

一、前言 对于一个usb摄像头&#xff0c;它的内核驱动源码位于/drivers/media/usb/uvc/ 核心层&#xff1a;V4L2_dev.c文件 硬件相关层&#xff1a; uvc_driver.c文件 本篇记录基于对6.8.8.8内核下vivid-core.c文件&#xff08;虚拟视频驱动程序&#xff09;的分析&#xff…

澳大利亚媒体发稿:怎样用图表提高易读性?-华媒舍

媒体发稿的可读性变得尤为重要。读者们不会再有时间与耐心去阅读文章繁琐的文本&#xff0c;他们更喜欢简洁明了的信息展现形式&#xff0c;在其中图表是一种极为高效的专用工具。下面我们就详细介绍怎么使用图表提高澳大利亚新闻媒体发稿的可读性&#xff0c;以适应读者的需要…