📄 retract.c
字号:
/*==============================================*/
else
{
lastPM = listOfPMs;
listOfPMs = listOfPMs->next;
}
}
/*===============================================*/
/* Return the last partial match in the new list */
/* of partial matches via one of the function's */
/* parameters. */
/*===============================================*/
*returnLast = lastPM;
/*=====================================================*/
/* Return the head of the new list of partial matches. */
/*=====================================================*/
return(head);
}
/***************************************************/
/* DeletePartialMatches: Returns a list of partial */
/* matches to the pool of free memory. */
/***************************************************/
static void DeletePartialMatches(
void *theEnv,
struct partialMatch *listOfPMs,
int betaDelete)
{
struct partialMatch *nextPM;
while (listOfPMs != NULL)
{
/*============================================*/
/* Remember the next partial match to delete. */
/*============================================*/
nextPM = listOfPMs->next;
/*================================================*/
/* Remove the links between the partial match and */
/* any data entities that it is attached to as a */
/* result of a logical CE. */
/*================================================*/
if (listOfPMs->dependentsf) RemoveLogicalSupport(theEnv,listOfPMs);
/*==========================================================*/
/* If the partial match is being deleted from a beta memory */
/* and the partial match isn't associated with a satisfied */
/* not CE, then it can be immediately returned to the pool */
/* of free memory. Otherwise, it's could be in use (either */
/* to retrieve variables from the LHS or by the activation */
/* of the rule). Since a not CE creates a "pseudo" data */
/* entity, the beta partial match which stores this pseudo */
/* data entity can not be deleted immediately (for the same */
/* reason an alpha memory partial match can't be deleted */
/* immediately). */
/*==========================================================*/
if (betaDelete &&
((listOfPMs->notOriginf == FALSE) || (listOfPMs->counterf)))
{ ReturnPartialMatch(theEnv,listOfPMs); }
else
{
listOfPMs->next = EngineData(theEnv)->GarbagePartialMatches;
EngineData(theEnv)->GarbagePartialMatches = listOfPMs;
}
/*====================================*/
/* Move on to the next partial match. */
/*====================================*/
listOfPMs = nextPM;
}
}
/**************************************************************/
/* ReturnPartialMatch: Returns the data structures associated */
/* with a partial match to the pool of free memory. */
/**************************************************************/
globle void ReturnPartialMatch(
void *theEnv,
struct partialMatch *waste)
{
/*==============================================*/
/* If the partial match is in use, then put it */
/* on a garbage list to be processed later when */
/* the partial match is not in use. */
/*==============================================*/
if (waste->busy)
{
waste->next = EngineData(theEnv)->GarbagePartialMatches;
EngineData(theEnv)->GarbagePartialMatches = waste;
return;
}
/*======================================================*/
/* If we're dealing with an alpha memory partial match, */
/* then return the multifield markers associated with */
/* the partial match (if any) along with the alphaMatch */
/* data structure. */
/*======================================================*/
if (waste->betaMemory == FALSE)
{
if (waste->binds[0].gm.theMatch->markers != NULL)
{ ReturnMarkers(theEnv,waste->binds[0].gm.theMatch->markers); }
rm(theEnv,waste->binds[0].gm.theMatch,(int) sizeof(struct alphaMatch));
}
/*=================================================*/
/* Remove any links between the partial match and */
/* a data entity that were created with the use of */
/* the logical CE. */
/*=================================================*/
if (waste->dependentsf) RemovePMDependencies(theEnv,waste);
/*======================================================*/
/* Return the partial match to the pool of free memory. */
/*======================================================*/
rtn_var_struct(theEnv,partialMatch,(int) sizeof(struct genericMatch *) *
(waste->bcount + waste->activationf + waste->dependentsf - 1),
waste);
}
/***************************************************************/
/* DestroyPartialMatch: Returns the data structures associated */
/* with a partial match to the pool of free memory. */
/***************************************************************/
globle void DestroyPartialMatch(
void *theEnv,
struct partialMatch *waste)
{
/*======================================================*/
/* If we're dealing with an alpha memory partial match, */
/* then return the multifield markers associated with */
/* the partial match (if any) along with the alphaMatch */
/* data structure. */
/*======================================================*/
if (waste->betaMemory == FALSE)
{
if (waste->binds[0].gm.theMatch->markers != NULL)
{ ReturnMarkers(theEnv,waste->binds[0].gm.theMatch->markers); }
rm(theEnv,waste->binds[0].gm.theMatch,(int) sizeof(struct alphaMatch));
}
/*================================================*/
/* Remove the alpha match used to represent a not */
/* CE match in a beta memory partial match. */
/*================================================*/
if ((waste->notOriginf) && (waste->counterf == FALSE))
{
if (waste->binds[waste->bcount - 1].gm.theMatch != NULL)
{
rtn_struct(theEnv,alphaMatch,
waste->binds[waste->bcount - 1].gm.theMatch);
}
}
/*=================================================*/
/* Remove any links between the partial match and */
/* a data entity that were created with the use of */
/* the logical CE. */
/*=================================================*/
if (waste->dependentsf) DestroyPMDependencies(theEnv,waste);
/*======================================================*/
/* Return the partial match to the pool of free memory. */
/*======================================================*/
rtn_var_struct(theEnv,partialMatch,(int) sizeof(struct genericMatch *) *
(waste->bcount + waste->activationf + waste->dependentsf - 1),
waste);
}
/******************************************************/
/* ReturnMarkers: Returns a linked list of multifield */
/* markers associated with a data entity matching a */
/* pattern to the pool of free memory. */
/******************************************************/
static void ReturnMarkers(
void *theEnv,
struct multifieldMarker *waste)
{
struct multifieldMarker *temp;
while (waste != NULL)
{
temp = waste->next;
rtn_struct(theEnv,multifieldMarker,waste);
waste = temp;
}
}
/*************************************************/
/* DriveRetractions: Filters the list of partial */
/* matches created as a result of removing a */
/* data entity through the join network. */
/*************************************************/
static void DriveRetractions(
void *theEnv)
{
struct rdriveinfo *tempDR;
struct joinNode *joinPtr;
while (EngineData(theEnv)->DriveRetractionList != NULL)
{
for (joinPtr = EngineData(theEnv)->DriveRetractionList->jlist;
joinPtr != NULL;
joinPtr = joinPtr->rightDriveNode)
{ NetworkAssert(theEnv,EngineData(theEnv)->DriveRetractionList->link,joinPtr,LHS); }
tempDR = EngineData(theEnv)->DriveRetractionList->next;
rtn_struct(theEnv,rdriveinfo,EngineData(theEnv)->DriveRetractionList);
EngineData(theEnv)->DriveRetractionList = tempDR;
}
}
/*************************************************/
/* RetractCheckDriveRetractions: */
/*************************************************/
globle void RetractCheckDriveRetractions( /* GDR 111599 #834 Begin */
void *theEnv,
struct alphaMatch *theAlphaNode,
int position)
{
struct rdriveinfo *tempDR, *theDR, *lastDR = NULL;
theDR = EngineData(theEnv)->DriveRetractionList;
while (theDR != NULL)
{
if ((position < (int) theDR->link->bcount) &&
(theDR->link->binds[position].gm.theMatch == theAlphaNode))
{
tempDR = theDR->next;
rtn_struct(theEnv,rdriveinfo,theDR);
if (lastDR == NULL)
{ EngineData(theEnv)->DriveRetractionList = tempDR; }
else
{ lastDR->next = tempDR; }
theDR = tempDR;
}
else
{
lastDR = theDR;
theDR = theDR->next;
}
}
} /* GDR 111599 #834 End */
/*************************************************************/
/* FlushGarbagePartialMatches: Returns partial matches and */
/* associated structures that were removed as part of a */
/* retraction. It is necessary to postpone returning these */
/* structures to memory because RHS actions retrieve their */
/* variable bindings directly from the fact and instance */
/* data structures through the alpha memory bindings. */
/*************************************************************/
globle void FlushGarbagePartialMatches(
void *theEnv)
{
struct partialMatch *pmPtr;
struct alphaMatch *amPtr;
/*===================================================*/
/* Return the garbage partial matches collected from */
/* the alpha memories of the pattern networks. */
/*===================================================*/
while (EngineData(theEnv)->GarbageAlphaMatches != NULL)
{
amPtr = EngineData(theEnv)->GarbageAlphaMatches->next;
rtn_struct(theEnv,alphaMatch,EngineData(theEnv)->GarbageAlphaMatches);
EngineData(theEnv)->GarbageAlphaMatches = amPtr;
}
/*==============================================*/
/* Return the garbage partial matches collected */
/* from the beta memories of the join networks. */
/*==============================================*/
while (EngineData(theEnv)->GarbagePartialMatches != NULL)
{
/*=====================================================*/
/* Remember the next garbage partial match to process. */
/*=====================================================*/
pmPtr = EngineData(theEnv)->GarbagePartialMatches->next;
/*=======================================================*/
/* If a "pseudo" data entity was created for the partial */
/* match (i.e. a not CE was satisfied), then dispose of */
/* the pseudo data entity. */
/*=======================================================*/
if ((EngineData(theEnv)->GarbagePartialMatches->notOriginf) &&
(EngineData(theEnv)->GarbagePartialMatches->counterf == FALSE))
{
if (EngineData(theEnv)->GarbagePartialMatches->binds[EngineData(theEnv)->GarbagePartialMatches->bcount - 1].gm.theMatch != NULL)
{
rtn_struct(theEnv,alphaMatch,
EngineData(theEnv)->GarbagePartialMatches->binds[EngineData(theEnv)->GarbagePartialMatches->bcount - 1].gm.theMatch);
}
}
/*============================================*/
/* Dispose of the garbage partial match being */
/* examined and move on to the next one. */
/*============================================*/
EngineData(theEnv)->GarbagePartialMatches->busy = FALSE;
ReturnPartialMatch(theEnv,EngineData(theEnv)->GarbagePartialMatches);
EngineData(theEnv)->GarbagePartialMatches = pmPtr;
}
}
#endif /* DEFRULE_CONSTRUCT */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -