⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 lgcldpnd.c

📁 VC嵌入式CLips专家系统,实现战场环境的目标识别
💻 C
📖 第 1 页 / 共 2 页
字号:
   /*******************************************************/
   /*      "C" Language Integrated Production System      */
   /*                                                     */
   /*             CLIPS Version 6.24  05/17/06            */
   /*                                                     */
   /*             LOGICAL DEPENDENCIES MODULE             */
   /*******************************************************/

/*************************************************************/
/* Purpose: Provide support routines for managing truth      */
/*   maintenance using the logical conditional element.      */
/*                                                           */
/* Principal Programmer(s):                                  */
/*      Gary D. Riley                                        */
/*                                                           */
/* Contributing Programmer(s):                               */
/*                                                           */
/* Revision History:                                         */
/*                                                           */
/*      6.24: Removed LOGICAL_DEPENDENCIES compilation flag. */
/*                                                           */
/*            Renamed BOOLEAN macro type to intBool.         */
/*                                                           */
/*            Rule with exists CE has incorrect activation.  */
/*            DR0867                                         */
/*                                                           */
/*************************************************************/

#define _LGCLDPND_SOURCE_

#include <stdio.h>
#define _STDIO_INCLUDED_

#include "setup.h"

#if DEFRULE_CONSTRUCT

#include "memalloc.h"
#include "router.h"
#include "envrnmnt.h"
#include "evaluatn.h"
#include "engine.h"
#include "reteutil.h"
#include "pattern.h"
#include "argacces.h"
#include "factmngr.h"

#if OBJECT_SYSTEM
#include "insfun.h"
#endif

#include "lgcldpnd.h"

/***************************************/
/* LOCAL INTERNAL FUNCTION DEFINITIONS */
/***************************************/

   static struct partialMatch    *FindLogicalBind(struct joinNode *,struct partialMatch *);
   static struct dependency      *DetachAssociatedDependencies(void *,struct dependency *,void *);

/***********************************************************************/
/* AddLogicalDependencies: Adds the logical dependency links between a */
/*   data entity (such as a fact or instance) and the partial match    */
/*   which logically supports that data entity. If a data entity is    */
/*   unconditionally asserted (i.e. the global variable TheLogicalJoin */
/*   is NULL), then existing logical support for the data entity is no */
/*   longer needed and it is removed. If a data entity is already      */
/*   unconditionally supported and that data entity is conditionally   */
/*   asserted (i.e. the global variable TheLogicalJoin is not NULL),   */
/*   then the logical support is ignored. Otherwise, the partial match */
/*   is linked to the data entity and the data entity is linked to the */
/*   partial match. Note that the word assert is used to refer to      */
/*   creating a fact with the assert command and creating an instance  */
/*   with the make-instance command.                                   */
/***********************************************************************/
globle intBool AddLogicalDependencies(
  void *theEnv,
  struct patternEntity *theEntity,
  int existingEntity)
  {
   struct partialMatch *theBinds;
   struct dependency *newDependency;

   /*==============================================*/
   /* If the rule has no logical patterns, then no */
   /* dependencies have to be established.         */
   /*==============================================*/

   if (EngineData(theEnv)->TheLogicalJoin == NULL)
     {
      if (existingEntity) RemoveEntityDependencies(theEnv,theEntity);
      return(TRUE);
     }
   else if (existingEntity && (theEntity->dependents == NULL))
     { return(TRUE); }

   /*============================================================*/
   /* Find the partial match in the logical join associated with */
   /* activation partial match. If the partial match cannot be   */
   /* found, then the partial match must have been deleted by a  */
   /* previous RHS action and the dependency link should not be  */
   /* added.                                                     */
   /*============================================================*/

   theBinds = FindLogicalBind(EngineData(theEnv)->TheLogicalJoin,EngineData(theEnv)->GlobalLHSBinds);
   if (theBinds == NULL) return(FALSE);

   /*==============================================================*/
   /* Add a dependency link between the partial match and the data */
   /* entity. The dependency links are stored in the partial match */
   /* behind the data entities stored in the partial match and the */
   /* activation link, if any.                                     */
   /*==============================================================*/

   newDependency = get_struct(theEnv,dependency);
   newDependency->dPtr = (void *) theEntity;
   newDependency->next = (struct dependency *)
                         theBinds->binds[theBinds->bcount + theBinds->activationf].gm.theValue;
   theBinds->binds[theBinds->bcount + theBinds->activationf].gm.theValue = (void *) newDependency;

   /*================================================================*/
   /* Add a dependency link between the entity and the partialMatch. */
   /*================================================================*/

   newDependency = get_struct(theEnv,dependency);
   newDependency->dPtr = (void *) theBinds;
   newDependency->next = (struct dependency *) theEntity->dependents;
   theEntity->dependents = (void *) newDependency;

   /*==================================================================*/
   /* Return TRUE to indicate that the data entity should be asserted. */
   /*==================================================================*/

   return(TRUE);
  }

/************************************************************************/
/* FindLogicalBind: Finds the partial match associated with the logical */
/*   CE which will provide logical support for a data entity asserted   */
/*   from the currently executing rule. The function is called when     */
/*   creating logical support links between the data entity and         */
/*   supporting partial matches. It compares each partial match found   */
/*   at a specified join to the partial match associated with a rule    */
/*   activation until it finds the partial match that generated the     */
/*   rule activation.                                                   */
/************************************************************************/
static struct partialMatch *FindLogicalBind(
  struct joinNode *theJoin,
  struct partialMatch *theBinds)
  {
   struct partialMatch *compPtr;
   unsigned int i;
   int found;

   /*==================================*/
   /* Loop through each of the partial */
   /* matches in the beta memory.      */
   /*==================================*/

   for (compPtr = theJoin->beta;
        compPtr != NULL;
        compPtr = compPtr->next)
     {
      /*==================================================*/
      /* Compare each of the data entities in the partial */
      /* match being examined and the partial match used  */
      /* in the dependency link.                          */
      /*==================================================*/

      found = TRUE;

      for (i = 0; i < compPtr->bcount; i++)
        {
         if (compPtr->binds[i].gm.theMatch != theBinds->binds[i].gm.theMatch)
           {
            found = FALSE;
            break;
           }
        }

      /*========================================================*/
      /* If all of the data entities in the partial match are   */
      /* identical to the partial match in the dependency link, */
      /* then this is the partial match we're looking for.      */
      /*========================================================*/

      if (found) return(compPtr);
     }

   /*========================================*/
   /* The partial match corresponding to the */
   /* logical dependency couldn't be found.  */
   /*========================================*/

   return(NULL);
  }

/*********************************************************************/
/* RemoveEntityDependencies: Removes all logical support links from  */
/*   a pattern entity that point to partial matches or other pattern */
/*   entities. Also removes the associated links from the partial    */
/*   matches or pattern entities which point back to the pattern     */
/*   entities.                                                       */
/*********************************************************************/
globle void RemoveEntityDependencies(
  void *theEnv,
  struct patternEntity *theEntity)
  {
   struct dependency *fdPtr, *nextPtr, *theList;
   struct partialMatch *theBinds;

   /*===============================*/
   /* Get the list of dependencies. */
   /*===============================*/

   fdPtr = (struct dependency *) theEntity->dependents;

   /*========================================*/
   /* Loop through each of the dependencies. */
   /*========================================*/

   while (fdPtr != NULL)
     {
      /*===============================*/
      /* Remember the next dependency. */
      /*===============================*/

      nextPtr = fdPtr->next;

      /*================================================================*/
      /* Remove the link between the data entity and the partial match. */
      /*================================================================*/

      theBinds = (struct partialMatch *) fdPtr->dPtr;
      theList = (struct dependency *)
                theBinds->binds[theBinds->bcount + theBinds->activationf].gm.theValue;
      theList = DetachAssociatedDependencies(theEnv,theList,(void *) theEntity);
      theBinds->binds[theBinds->bcount + theBinds->activationf].gm.theValue = (void *) theList;

      /*========================*/
      /* Return the dependency. */
      /*========================*/

      rtn_struct(theEnv,dependency,fdPtr);

      /*=================================*/
      /* Move on to the next dependency. */
      /*=================================*/

      fdPtr = nextPtr;
     }

   /*=====================================================*/
   /* Set the dependency list of the data entity to NULL. */
   /*=====================================================*/

   theEntity->dependents = NULL;
  }
  
/********************************************************************/
/* ReturnEntityDependencies: Removes all logical support links from */
/*   a pattern entity. This is unidirectional. The links from the   */
/*   the partial match to the entity are not removed.               */
/********************************************************************/
globle void ReturnEntityDependencies(
  void *theEnv,
  struct patternEntity *theEntity)
  {
   struct dependency *fdPtr, *nextPtr;

   fdPtr = (struct dependency *) theEntity->dependents;

   while (fdPtr != NULL)
     {
      nextPtr = fdPtr->next;
      rtn_struct(theEnv,dependency,fdPtr);
      fdPtr = nextPtr;
     }

   theEntity->dependents = NULL;
  }

/*******************************************************************/
/* DetachAssociatedDependencies: Removes all logical support links */
/*   which pointer to a pattern entity from a list of dependencies */
/*   (which may be associated with either a partial match or       */
/*   another pattern entity). Does not remove links which point in */
/*   the other direction.                                          */
/*******************************************************************/
static struct dependency *DetachAssociatedDependencies(
  void *theEnv,
  struct dependency *theList,
  void *theEntity)
  {
   struct dependency *fdPtr, *nextPtr, *lastPtr = NULL;

   fdPtr = theList;

   while (fdPtr != NULL)
     {
      if (fdPtr->dPtr == theEntity)
        {
         nextPtr = fdPtr->next;
         if (lastPtr == NULL) theList = nextPtr;
         else lastPtr->next = nextPtr;
         rtn_struct(theEnv,dependency,fdPtr);
         fdPtr = nextPtr;
        }
      else
        {
         lastPtr = fdPtr;
         fdPtr = fdPtr->next;
        }
     }

   return(theList);
  }

/**************************************************************************/
/* RemovePMDependencies: Removes all logical support links from a partial */
/*   match that point to any data entities. Also removes the associated   */
/*   links from the data entities which point back to the partial match.  */
/**************************************************************************/
globle void RemovePMDependencies(
  void *theEnv,
  struct partialMatch *theBinds)
  {
   struct dependency *fdPtr, *nextPtr, *theList;
   struct patternEntity *theEntity;

   fdPtr = (struct dependency *) theBinds->binds[theBinds->bcount + theBinds->activationf].gm.theValue;

   while (fdPtr != NULL)
     {

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -