Search code examples
prologdcg

"Returning" a list from a predicate in Prolog


resolve(K, K, _) :- writeln('finished'). %goal state

resolve(CurrentState, GoalState, Path) :-
    suc(_, CurrentState, NextState, GoalState),
    append(Path, [CurrentState], NextPath),
    resolve(NextState, GoalState, NewPath).

I currently have this algorithm, and it works as it should. I am running it like this:

resolve(0, 10, Path).

I know for sure that the algorithm is running as it should, it gets to the goal state, although Path's value is

Path = []

which is not what should happen. Path should contain the sequence of "states" in which my algorithm has passed. What might be the problem?


Solution

  • It's easiest to use DCG notation to describe the list:

    path(State0, Target) -->
        (    { State0 == Target } -> []
        ;    { suc(_, State0, State1, Target) },
             [State1],
             path(State1, Target)
        ).
    

    You can also do it manually:

    path(State0, Target, Path) :-
        (    State0 == Target -> Path = []
        ;    suc(_, State0, State1, Target),
             Path = [State1|Rest],
             path(State1, Target, Rest)
        ).
    

    There is no need for accumulators here to get linear time.