如何在Drools规则的when部分调用Java函数并存储Set到变量
解决Drools规则中调用Java函数并接收返回Set的问题
问题说明
需要在Drools规则的when部分调用Java函数getSet(List<Something>),将返回的Set存入变量$variable,但当前$variable始终为空,无法正常使用。原规则代码如下:
import com.example.ClassName(); import com.example.more.ObjectThings(); rule "Example" when $object: ClassName(); $listOfObjcts: Set() from collect( ObjectThings() from GetSetOfSomething($object)); // 调用并保存目标集合。$variable为空。 $variable: Set() from $object.getSet($listOfObjcts); // 一种不够优雅的获取集合的方式: $set: Set() from collect( String() from $object.getSet($listObjects)); // 此字符串包含目标集合的字符串形式。 $string: String() from String.join(",", $object.getSet($listOfObjcts)); then System.out.println("List of objects: " + $variable); end
对应的Java函数定义:
public Set<String> getSet(List<Something> items) { if (items == null) { return emptySet(); } Set<String> nameList = new HashSet<>(); for (Something item : items) { nameList.add(item.getName()); } return nameList; }
注:GetSetOfSomething返回结果正确,$listOfObjcts已正确填充。
问题原因
核心问题是参数类型不匹配:$listOfObjcts是Set类型,但getSet方法的参数要求是List类型,导致函数调用时无法正确传入参数,最终返回空集合或绑定变量失败。另外原代码中存在变量名笔误($listObjects应为$listOfObjcts)。
解决方案
1. 修正参数类型
将Set类型的$listOfObjcts转换为List后传入getSet方法,Drools支持直接在规则中使用Java集合类的构造方法完成转换。
2. 正确绑定返回值
直接通过from关键字将函数返回的Set绑定到变量,无需额外的collect操作(除非需要拆分集合元素)。
修正后的规则代码
import com.example.ClassName; import com.example.more.ObjectThings; import java.util.ArrayList; import java.util.Set; rule "Example" when $object: ClassName(); $listOfObjcts: Set() from collect( ObjectThings() from GetSetOfSomething($object)); // 将Set转为List传入getSet,正确绑定返回的Set到$variable $variable: Set() from $object.getSet(new ArrayList($listOfObjcts)); then System.out.println("List of objects: " + $variable); end
额外说明
- 如果可以修改Java函数
getSet的参数类型为Collection<Something>,则无需转换,直接传入$listOfObjcts即可,代码会更简洁。 - 原代码中
collect(String() from $object.getSet(...))的方式虽然可行,但属于冗余操作,直接绑定返回的Set是更高效优雅的写法。
内容的提问来源于stack exchange,提问作者MR.ROBOT
相关产品推荐
相关产品推荐

