POINTER st_ExistGenPreTest(CONTEXT IndexContext, st_INDEX StIndex, TERM Term) /************************************************************** INPUT: RETURNS: EFFECTS: ***************************************************************/ { SYMBOL FirstDomain; POINTER Result; #ifdef CHECK if (!st_StackEmpty(st_STACKSAVE)) { misc_StartErrorReport(); misc_ErrorReport("\n In st_ExistGenPreTest: ST-Stack not empty.\n"); misc_FinishErrorReport(); } else if (st_CURRENT_RETRIEVAL != st_NOP) { misc_StartErrorReport(); misc_ErrorReport("\n In st_ExistGenPreTest: %d Retrieval already in progress.\n", st_CURRENT_RETRIEVAL); misc_FinishErrorReport(); } #endif cont_Check(); if (st_Exist(StIndex)) { st_CURRENT_RETRIEVAL = st_GENPRETEST; st_WHICH_CONTEXTS = st_STANDARD; st_INDEX_CONTEXT = IndexContext; st_STACKSAVE = st_StackBottom(); FirstDomain = symbol_FirstIndexVariable(); st_EXIST_MINMAX = term_ComputeSize(Term); cont_CreateBinding(IndexContext, FirstDomain, IndexContext, Term); cont_StartBinding(); st_StackPush(StIndex->subnodes); cont_StartBinding(); Result = st_TraverseForExistGenPreTest(IndexContext); #ifdef CHECK cont_SaveState(); #endif if (Result == NULL) st_CancelExistRetrieval(); return Result; } else return NULL; }
static LIST st_TraverseTreeGenPreTest(CONTEXT IndexContext, st_INDEX StIndex, st_MINMAX MinMax) /************************************************************** INPUT: RETURNS: EFFECTS: ***************************************************************/ { int Save; LIST Result, CurrentList; st_INDEX CurrentNode; /* PREPARE TRAVERSAL */ Save = stack_Bottom(); Result = list_Nil(); CurrentList = StIndex->subnodes; cont_StartBinding(); for (;;) { /* BACKTRACK A BIG STEP */ if (list_Empty(CurrentList)) { cont_StopAndBackTrack(); if (stack_Empty(Save)) return Result; CurrentList = stack_PopResult(); } /* DESCENDING */ for (CurrentNode = (st_INDEX)list_Car(CurrentList); (MinMax >= st_Min(CurrentNode)) && subst_Match(IndexContext, CurrentNode->subst); CurrentList = CurrentNode->subnodes, CurrentNode = (st_INDEX)list_Car(CurrentList)) if (st_IsLeaf(CurrentNode)) { Result = list_Append(CurrentNode->entries, Result); break; } else if (list_Cdr(CurrentList)) { stack_Push(list_Cdr(CurrentList)); cont_StartBinding(); } else cont_StopAndStartBinding(); /* BACKTRACK LEAF OR INNER NODE */ CurrentList = list_Cdr(CurrentList); cont_BackTrackAndStart(); } }
static st_INDEX st_FirstVariant(const CONTEXT Context, LIST Subnodes, st_INDEX* BestNonVariant) /************************************************************** INPUT: RETURNS: EFFECTS: ***************************************************************/ { st_INDEX EmptyVariant; for (EmptyVariant = NULL, *BestNonVariant = NULL; list_Exist(Subnodes); Subnodes = list_Cdr(Subnodes)) { st_INDEX CurrentNode; CurrentNode = (st_INDEX)list_Car(Subnodes); cont_StartBinding(); if (subst_Variation(Context, CurrentNode->subst)) { if (subst_Exist(CurrentNode->subst)) { subst_CloseVariables(Context, CurrentNode->subst); return CurrentNode; } else EmptyVariant = CurrentNode; } else if (*BestNonVariant == NULL) if (subst_MatchTops(Context, CurrentNode->subst)) *BestNonVariant = CurrentNode; cont_BackTrack(); } return EmptyVariant; }
static POINTER st_TraverseForExistInstancePreTest(CONTEXT IndexContext) /************************************************************** INPUT: RETURNS: EFFECTS: ***************************************************************/ { LIST CurrentList; st_INDEX CurrentNode; /* Caution: In case an entry is found the procedure returns immediately without backtracking the current bindings. */ CurrentList = list_Nil(); for (;;) { /* BACKTRACK A BIG STEP */ if (list_Empty(CurrentList)) { cont_StopAndBackTrack(); if (st_StackEmpty(st_STACKSAVE)) return NULL; CurrentList = st_StackPopResult(); } /* DESCENDING */ for (CurrentNode = (st_INDEX)list_Car(CurrentList); (st_EXIST_MINMAX <= st_Max(CurrentNode)) && subst_MatchReverse(IndexContext, CurrentNode->subst); CurrentList = CurrentNode->subnodes, CurrentNode = (st_INDEX)list_Car(CurrentList)) { if (list_Exist(list_Cdr(CurrentList))) { st_StackPush(list_Cdr(CurrentList)); cont_StartBinding(); } else cont_StopAndStartBinding(); if (st_IsLeaf(CurrentNode)) { st_StackPush(list_Cdr(CurrentNode->entries)); return list_Car(CurrentNode->entries); } } /* BACKTRACK LEAF OR INNER NODE */ CurrentList = list_Cdr(CurrentList); cont_BackTrackAndStart(); } }
LIST cond_CondFast(CLAUSE c) /********************************************************** INPUT: A clause c. RETURNS: A list with indexes with respect to c that can be deleted due to condensing. CAUTION: None. ***********************************************************/ { int vec, i, j, k; LIST indexlist; indexlist = list_Nil(); vec = vec_ActMax(); for (i = 0; i < clause_Length(c); i++) { vec_Push((POINTER) i); } for (k = clause_Length(c) - 1; k >= 0; k--) { for (i = vec; i < vec_ActMax(); i++) { if ((int)vec_GetNth(i) != k) { cont_StartBinding(); if (unify_Match(cont_LeftContext(), clause_GetLiteralTerm(c,k), clause_GetLiteralTerm(c,(int)vec_GetNth(i)))) { cont_BackTrack(); for (j = vec; j < vec_ActMax(); j++) { if (k == (int)vec_GetNth(j)) { vec_Swap((vec_ActMax() -1) ,j); j = vec_ActMax(); } } if (subs_IdcRes(c,vec,(vec_ActMax() -1))) { indexlist = list_Cons((POINTER)k,indexlist); vec_Pop(); } i = vec_ActMax()+1; } else cont_BackTrack(); } } } vec_SetMax(vec); return indexlist; }
BOOL cont_BindingsAreRenamingModuloMatching(const CONTEXT RenamingContext) { CONTEXT Context; #ifdef CHECK if (!cont_IsContextEmpty(RenamingContext)) { misc_StartErrorReport(); misc_ErrorReport("\n In cont_BindingsAreRenamingModuloMatching:"); misc_ErrorReport(" Renaming context contains bindings.\n"); misc_FinishErrorReport(); } #endif cont_StartBinding(); Context = cont_LastBinding(); while (Context) { if (!symbol_IsIndexVariable(cont_BindingSymbol(Context))) { SYMBOL CodomainSymbol; CodomainSymbol = term_TopSymbol(cont_BindingTerm(Context)); if (symbol_IsVariable(CodomainSymbol)) { if (cont_VarIsRenamed(RenamingContext, CodomainSymbol)) { cont_BackTrack(); return FALSE; } else { cont_CreateBinding(RenamingContext, CodomainSymbol, NULL, NULL); cont_SetContextBindingRenaming(RenamingContext, CodomainSymbol, CodomainSymbol); } } else { cont_BackTrack(); return FALSE; } } Context = cont_BindingLink(Context); } cont_BackTrack(); return TRUE; }
BOOL st_EntryDelete(st_INDEX StIndex, POINTER Pointer, TERM Term, const CONTEXT Context) /************************************************************** INPUT: RETURNS: EFFECTS: ***************************************************************/ { BOOL Found; LIST Subnodes; SYMBOL FirstDomain; cont_Check(); FirstDomain = symbol_FirstIndexVariable(); cont_CreateBinding(Context, FirstDomain, Context, Term); for (Found = FALSE, Subnodes = StIndex->subnodes; list_Exist(Subnodes); Subnodes = list_Cdr(Subnodes)) { st_INDEX CurrentNode; CurrentNode = (st_INDEX)list_Car(Subnodes); cont_StartBinding(); if (subst_Variation(Context, CurrentNode->subst)) { list_Rplaca(Subnodes, st_EntryDeleteHelp(Context, CurrentNode, Pointer, &Found)); if (Found) { StIndex->subnodes = list_PointerDeleteElement(StIndex->subnodes, NULL); if (list_Exist(StIndex->subnodes)) { CurrentNode = (st_INDEX)list_Car(StIndex->subnodes); st_SetMax(StIndex, st_Max(CurrentNode)); st_SetMin(StIndex, st_Min(CurrentNode)); for (Subnodes = list_Cdr(StIndex->subnodes); list_Exist(Subnodes); Subnodes = list_Cdr(Subnodes)) { CurrentNode = (st_INDEX)list_Car(Subnodes); if (st_Max(CurrentNode) > st_Max(StIndex)) st_SetMax(StIndex, st_Max(CurrentNode)); if (st_Min(CurrentNode) < st_Min(StIndex)) st_SetMin(StIndex, st_Min(CurrentNode)); } } else { st_SetMax(StIndex, 0); st_SetMin(StIndex, 0); } break; } } cont_BackTrack(); } cont_Reset(); return Found; }
static st_INDEX st_EntryDeleteHelp(const CONTEXT Context, st_INDEX StIndex, POINTER Pointer, BOOL* Found) /************************************************************** INPUT: The root of an abstraction tree (StIndex), a pointer to a specific entry of the tree and a query term. RETURNS: Nothing. SUMMARY: Uses Term in order to find Pointer in the tree. EFFECTS: Will delete nodes of StIndex. ***************************************************************/ { if (st_IsLeaf(StIndex)) { *Found = list_DeleteFromList(&(StIndex->entries), Pointer); if (list_Exist(StIndex->entries)) return StIndex; else { subst_Delete(StIndex->subst); st_Free(StIndex); return NULL; } } else { LIST Subnodes; for (Subnodes = StIndex->subnodes; list_Exist(Subnodes); Subnodes = list_Cdr(Subnodes)) { st_INDEX CurrentNode; CurrentNode = (st_INDEX)list_Car(Subnodes); cont_StartBinding(); if (subst_Variation(Context, CurrentNode->subst)) { list_Rplaca(Subnodes, st_EntryDeleteHelp(Context, CurrentNode, Pointer, Found)); if (*Found) { if (list_DeleteFromList(&(StIndex->subnodes), NULL)) if (list_Empty(list_Cdr(StIndex->subnodes))) { /* 'StIndex' has one subnode only. */ st_NodeMergeWithSon(StIndex); return StIndex; } /* Assertion: 'StIndex' is an inner node. */ CurrentNode = (st_INDEX)list_Car(StIndex->subnodes); st_SetMax(StIndex, st_Max(CurrentNode)); st_SetMin(StIndex, st_Min(CurrentNode)); for (Subnodes = list_Cdr(StIndex->subnodes); list_Exist(Subnodes); Subnodes = list_Cdr(Subnodes)) { CurrentNode = (st_INDEX)list_Car(Subnodes); if (st_Max(CurrentNode) > st_Max(StIndex)) st_SetMax(StIndex, st_Max(CurrentNode)); if (st_Min(CurrentNode) < st_Min(StIndex)) st_SetMin(StIndex, st_Min(CurrentNode)); } return StIndex; } } cont_BackTrack(); } return StIndex; } }