0

I am attempting to create a maze program in Prolog, whereby the aim is to find a route from the start of the maze to a point in the centre of the maze called m. The maze consists of squares which are connected using one of four colours: Blue, Green, Purple or Orange. The route from start to the centre follows a repeating pattern of the four colours.

I have created the following code:

link2(A, Colour, B) :- link(A, Colour, B).       
link2(A, Colour, B) :- link(B, Colour, A).

changecolour(blue,green).
changecolour(green,purple).
changecolour(purple,orange).
changecolour(orange,blue).

route(A, Colour1, B, List2) :-
    link2(A, Colour1, B),
    append([A], [B], List2).
route(A, Colour1, B, List2) :-
    link2(A, Colour1, X),
    changecolour(Colour1,Colour2),
    append([A], List, List2),
    \+ member(A, List),
    route(X, Colour2, B, List).

For some reason, the code isn't working as expected and I'm not sure why. I have a feeling its something to do with the negation(not member) rule but can someone advise what I'm doing wrong?

  • 1
    What is it doing, and what were you expecting? – Scott Hunter Apr 26 '16 at 13:34
  • 2
    Use `maplist(dif(A), Ls)` to express, in a purely logical way, that `A` is not in the list `Ls`. – mat Apr 26 '16 at 13:36
  • I'm aiming for the prolog to print out the route from start to m, however, when I run the trace, Prolog asks whether start is a member of a list which is just a variable, _G449 so returns > Exit: (8) lists:member(start, [start|_G452]) ? creep. Exit means success, but since we have “not member” in this instance, exiting member successfully means to fail here. "Not member" should only fail if the program comes back to a square that has already been visited. – m.lewis1995 Apr 26 '16 at 13:36
  • Ask Java? Just an aside: instead of `append([A], List, List2)` you can just say, `[A|List] = List2`, and instead of `append([A], [B], List2)`, just, `[A,B] = List2`, or briefer still: `route(A, Colour1, B, [A,B]) :- link2(A, Colour1, B).` (NOTE: you have a typo and wrote `Colou1` instead of `Colour1`). – lurker Apr 26 '16 at 13:38
  • So I replace \+ member(A, List) with maplist(dif(A), Ls)? – m.lewis1995 Apr 26 '16 at 13:52
  • 2
    No, you'd replace `\+ member(A, List)` with `maplist(dif(A), List)`. – lurker Apr 26 '16 at 14:05
  • 1
    @lurker There are definitely many answers on SO by mat, false, repeat that use this idiom. –  Apr 26 '16 at 14:08
  • @m.lewis1995 You still haven't said what query you entered, what result you got, and what result you expected. – lurker Apr 26 '16 at 14:10
  • @Boris yeah somehow I missed that specific form. Not sure why. Bad eyesight I guess... or bad memory. Time for me to go back to my cave. :p – lurker Apr 26 '16 at 14:15
  • The query was ?-route(Start, Blue, m, List2). I expected it to output the route from start to m (there are many cycles and I believe that there are many steps in this route). The query returned false. – m.lewis1995 Apr 26 '16 at 14:18
  • @lurker I've only noticed it because usually, you either want `\+ memberchk` if you know the list is ground, or then really `maplist(dif)` if you don't. `\+ member` is not too useful I guess? –  Apr 26 '16 at 14:31
  • @m.lewis1995 that query will be a problem. `Blue` is a variable. Did you mean `route(Start, blue, m, List2).`? – lurker Apr 26 '16 at 14:32
  • Apologies, you are correct. – m.lewis1995 Apr 26 '16 at 14:39

1 Answers1

0

You defined changecolour and never used it; you used nextcolour but never defined it.

Scott Hunter
  • 48,888
  • 12
  • 60
  • 101
  • This was an error when I typed my query into Stack overflow. It was correct in the program. – m.lewis1995 Apr 26 '16 at 13:45
  • @m.lewis1995 it would help a great deal if you copy/paste the actual code into your question that you're having trouble with. – lurker Apr 26 '16 at 14:02
  • @m.lewis1995 not necessarily *all* of the code, but at least what you put there should be accurate. – lurker Apr 26 '16 at 14:06