在CLIPS中获取议程

时间:2017-03-07 15:50:30

标签: rule-engine clips

我与CLIPS.NET合作,并想知道如何以剪辑方式访问议程。

我希望有一些输入值并让剪辑运行,以便它可以根据输入值生成解决方案。但我也想看看究竟是什么规则被解雇了。我现在有类似的东西

(deftemplate MAIN::action
  (slot name (default ?NONE)))

(deftemplate MAIN::input
  (slot name)
  (slot value (default ?NONE)))

(defrule MAIN::rule0
  (input (name test-input) (value 1))
=>
  (assert (action (name do-something)))
)

问题是我无法使用(议程),因为它只会向控制台打印一些东西,并且不会给我任何可以使用的字符串或类似的东西。所以 我怎么能得到议程?或者我是否需要在每个规则中创建一个新事实,以查看执行的规则(看起来有点不方便)? (现在我只需要规则的名称)

更新

我尝试功能“all-next-activation”(现在正在工作):

void AllNextActivationFunction(
    void *theEnv,
    DATA_OBJECT_PTR returnValue)
    {
    unsigned long count;
    struct multifield *theList;
    void *act;


    if (EnvArgCountCheck(theEnv, "all-next-activation", EXACTLY, 0) == -1)
        {
        EnvSetMultifieldErrorValue(theEnv, returnValue);
        return;
        }

    // Count activations
    for (act = EnvGetNextActivation(theEnv, NULL), count = 0;
        act != NULL;
        act = EnvGetNextActivation(theEnv, act), count++)
        { /* Do Nothing */ }

    // Create the multifield
    SetpType(returnValue, MULTIFIELD);
    SetpDOBegin(returnValue, 1);
    SetpDOEnd(returnValue, (long)count);
    theList = (struct multifield *) EnvCreateMultifield(theEnv, count);
    SetpValue(returnValue, (void *)theList);

    // Store values in multifield
    for (act = EnvGetNextActivation(theEnv, NULL), count = 1;
        act != NULL;
        act = EnvGetNextActivation(theEnv, act), count++)
        {
        SetMFType(theList, count, SYMBOL);
        SetMFValue(theList, count, EnvAddSymbol(theEnv, EnvGetActivationName(theEnv, act)));
        }
    }


void EnvUserFunctions(
  void *environment)
  {
    EnvDefineFunction2(environment, "next-activation", 'w', PTIEF NextActivationFunction, "NextActivationFunction", "00");
    EnvDefineFunction2(environment, "all-next-activation", 'm', PTIEF AllNextActivationFunction, "AllNextActivationFunction", "00");
  }

1 个答案:

答案 0 :(得分:2)

您必须扩展.NET API以包含一些C函数,这些函数允许您迭代激活并从中获取信息或在CLIPS中添加用户定义的函数并使用Eval方法。 NET调用CLIPS函数。例如,这里可以添加到userfunctions.c的代码,它返回下一次激活的名称:

void *NextActivationFunction(
  void *theEnv)
  {
   void *act;

   if (EnvArgCountCheck(theEnv,"next-activation",EXACTLY,0) == -1)
     { return EnvFalseSymbol(theEnv); }

   act = EnvGetNextActivation(theEnv,NULL);

   if (act == NULL)
     { return EnvFalseSymbol(theEnv); }
   else
     { return EnvAddSymbol(theEnv,EnvGetActivationName(theEnv,act)); }
  }

void EnvUserFunctions(
  void *environment)
  {
   EnvDefineFunction2(environment,"next-activation", 'w', PTIEF NextActivationFunction, "NextActivationFunction", "00");
  }

使用该代码重新编译CLIPS允许您在CLIPS中使用此功能:

CLIPS> (next-activation)
FALSE
CLIPS> (defrule foo =>)
CLIPS> (defrule bar =>)
CLIPS> (next-activation)
bar
CLIPS> (run 1)
CLIPS> (next-activation)
foo
CLIPS> 

或者使用Eval方法从.NET开始:

clips.Eval("(next-activation)");