예제 #1
0
        private static Goal CreateGoal(ArgumentInstantiator visitor, Compiled.Goal goalDef)
        {
            var arguments = goalDef.Arguments.Select(a => a.Accept(visitor)).ToArray();

            var predicate = goalDef.Predicate;

            var goal = predicate.Accept(new GoalInstantiator());

            goal.Arguments  = arguments;
            goal.Definition = goalDef;

            goal.Restart();

            return(goal);
        }
예제 #2
0
        Frame Unify(Compiled.Clause clause)
        {
            var boundVariables       = new BoundVariableSet();
            var argumentInstantiator = new ArgumentInstantiator();

            var clauseHeadArguments = clause.Head.Arguments.Select(a => a.Accept(argumentInstantiator)).ToArray();

            if (boundVariables.ZipUnify(Arguments, clauseHeadArguments))
            {
                Goal [] goals = EngineInternals.InstantiateGoals(clause.Body, argumentInstantiator);

                return(new Frame(goals, this, boundVariables, argumentInstantiator.Variables));
            }

            return(null);
        }
예제 #3
0
// ReSharper disable ParameterTypeCanBeEnumerable.Global
        internal static Goal [] InstantiateGoals(Compiled.Goal [] goalDefs, ArgumentInstantiator argumentInstantiator)
// ReSharper restore ParameterTypeCanBeEnumerable.Global
        {
            return(goalDefs.Select(goalDef => CreateGoal(argumentInstantiator, goalDef)).ToArray());
        }
예제 #4
0
        public IEnumerable <IDebugEvent> Solve(Compiled.Goal [] goalDefs)
        {
            // Instantiate the goals.
            var queryArgumentInstantiator = new ArgumentInstantiator();
            var goals = InstantiateGoals(goalDefs, queryArgumentInstantiator);

            frame = new Frame(goals, null, new BoundVariableSet(), queryArgumentInstantiator.Variables);

// ReSharper disable ConditionIsAlwaysTrueOrFalse
            while (frame != null)
// ReSharper restore ConditionIsAlwaysTrueOrFalse
            {
                if (frame.GoalsProven == frame.Goals.Length)
                {
                    // No more goals to prove or it's a fact.
                    System.Diagnostics.Debug.Assert(frame.Goals.All(g => g.CurrentFrame != null));

                    if (frame.Parent == null)
                    {
                        yield return(new Solution(frame));

                        foreach (var e in GoToLastChoicePoint())
                        {
                            yield return(e);
                        }
                    }
                    else
                    {
                        // go on and prove the next parent goal.
                        frame = frame.Parent;
                        frame.GoalsProven++;
                    }

                    continue;
                }

                var goal = frame.Goals [frame.GoalsProven];

                // Check that the same goal is not on the stack to prevent infinite loops.
                if (AlreadyOnTheStack(goal))
                {
                    foreach (var e in Backtrack())
                    {
                        yield return(e);
                    }
                }
                else
                {
                    var newFrame = goal.GetNextFrame();

                    if (newFrame == null)
                    {
                        foreach (var e in Backtrack())
                        {
                            yield return(e);
                        }
                    }
                    else
                    {
                        yield return(new Enter(newFrame));

                        frame = newFrame; // decend the tree
                    }
                }
            }
        }