Prolog print statement does not work as expected - prolog

I was trying to define a functor and print each individual items of list in Prolog, but Prolog is not printing in correct format.
rint(L):-
write(H).
the output is like
rint([a, s,v ,c]).
_L139
true.
This is what I expect to achieve by calling the functor, any help or thought is appreciated, I'm new to Prolog and learning it.
?- rint([a,b,c,d]).
.(a, .(b, .(c, .(d, []))))

I think it should be
rint(L) :- write(L).
Also if you want .(a, .(b, .(c, .(d, [])))) and not [a, b, c, d] in output, use display:
rint(L) :- display(L).

The problem is an error in your rule for rint.
Your definition says that rint(L) succeeds if write(H) succeeds. At that point, the interpreter knows nothing about H. So it writes a value it doesn't know, which is why you see the _L139, the internal representation of an uninitialised variable.
Having done that, write(H) has succeed, is true, so rint(L) is true. The interpreter tells you that: true.
To define your own rint/1 without relying on built-ins such as display/1, you would need to do something like
rint([]) :-
write([]).
rint([H|T]) :-
write('.('),
write(H),
write(', '),
rint(T),
write(')').
If you're trying to display an empty list, just write it. If you're trying to display any other list, write the opening period and parenthesis, write the Head, write the following comma and space, then call itself for the Tail of the list, then write the closing parenthesis.

Related

Representing truth regarding beliefs in prolog

How to make this (or something similar) work in Prolog:
belief(john,red(apple)).
belief(peter,red(apple)).
X :- belief(john,X), belief(peter,X).
And get true. for the following query (while consulting above):-
?- red(apple).
First, it's useful to define a little helper to capture when all (relevant) persons believe something:
all_believe(Belief) :-
belief(john, Belief),
belief(peter, Belief).
Then you can define, for example:
red(Object) :-
all_believe(red(Object)).
green(Object) :-
all_believe(green(Object)).
And with your given set of beliefs you get:
?- red(apple).
true.
?- green(apple).
false.
This works. It requires you to define similar rules for any term that you want to use as a belief.
You can make this a bit shorter with macro definitions using term_expansion:
term_expansion(declare_belief(Belief),
Belief :- all_believe(Belief)).
This means that every top-level definition in your source code of the form declare_belief(Belief) should be treated as if you had written Belief :- all_believe(Belief) instead (with the variable Belief substituted appropriately).
So now you can just write this:
declare_belief(red(_)).
declare_belief(green(_)).
and it will be treated exactly like the longer definitions for red(Object) and red(Object) above. You will still have to write this kind of declaration for any term that you want to use as a possible belief.
Prolog does not allow the head of a rule to be just a variable. The head must be a nonvar term, whose functor (i.e., name and arity) identifies the predicate being defined. So, a possible solution would be something like this:
true_belief(X) :-
belief(john, X),
belief(peter, X).
belief(john, red(apple)).
belief(peter, red(apple)).
Examples:
?- true_belief(red(apple)).
true.
?- true_belief(X).
X = red(apple).

Prolog singleton variables in rule head causes program to output booleans for all queries

I have this prolog program.
red(rose).
red(anthurium).
white(rose).
white(gardenia).
white(jasmine).
like(Y,X) :-
red(X),!,
fail
;
white(X).
And below is how it responds to different queries.
?- like(rose,gardenia).
true.
?- like(rose,P).
false.
?- like(Val,anthurium).
false.
?- like(rose,X).
false
The problem I now have is this:
When querying with a variable within the query (Eg: ?- like(rose,X).), Prolog usually responds by returning a value, (something like X=some_val). Why I don't get any value for those variables, but either true or false?
All helpful answers are highly appreciated. Thanks in advance.
Think about what Prolog is doing here:
like(rose,P) succeeds if red(P), so it grabs a possible substitution for P, namely rose or anthurium. Then it traverses the cut and then it fails. But "failing" means that the proof search down that path didn't bring any solution, there are no successful bindings to report (the only fail to get information out of a failing branch is to side-effect to a log file and read check it later). In fact, all bindings will be undone on backtracking. The second branch is white(X), but rose is not white, so we fail here, too.
You can also write:
like(_,X) :- \+ red(X).
like(_,X) :- white(X).
which is a bit more readable. One notices that when calling like(_,X), the goal enclosed by the negation-as-failure operator \+ is nonground. This is bad, and causes a floundering query (in other words, don't do that). I have written this little page on "floundering".

My Swi-prolog code return true for every query

I'm trying to write Swi-Prolog code for family relations. There are no error but it always returns true. P
man(_Pete).
man(_Mark).
man(_John).
man(_Frank).
man(_Tom).
man(_Matt).
man(_Henry).
man(_Todd).
woman(_Lilly).
woman(_Kate).
woman(_Anne).
woman(_Alice).
woman(_Jenny).
parent(_Pete,_Mark).
parent(_Pete,_Tom).
parent(_Pete,_Anne).
parent(_Mark,_Lilly).
parent(_Mark,_John).
parent(_Mark,_Frank).
parent(_Tom,_Kate).
parent(_Anne,_Alice).
parent(_Anne,_Matt).
parent(_Alice,_Henry).
parent(_Matt,_Jenny).
parent(_Matt,_Todd).
father(X,Y) :- man(X),parent(X,Y).
mother(X,Y) :- woman(X),parent(X,Y).
sibling(X,Y) :- parent(Z,X),parent(Z,Y).
sister(X,Y) :- woman(X),sibling(X,Y).
brother(X,Y) :- man(X), sibling(X,Y).
grandparent(X,Y) :- parent(X,Z),parent(Z,Y).
I'm expecting to check relations. Like if I try a function ?- parent(Pete,John). I believe it should return false, but it actually returns true for every query. This is my first program on Prolog and might need help to understand the problem.
You probably meant to write names but instead you put anonymous variables in there.
Instead of parent(_Matt,_Todd) you should write parent('Matt', 'Todd') or even parent(matt, todd).
This is an anonymous variable: _X.
This is a normal variable: X.
This is a lower-case atom. It is has a length of 1, so it is also a "char": x.
This is an upper-case char: 'X'.
If you wrap anything in single quotes, it becomes an atom. It can also have spaces in it.
If you put an underscore at the front, you get an anonymous variable. It ends at the first space or operator.
If you are getting "Singleton variable" warnings, it is usually one of two things.
Beginners often mean to write 'Bob' but write Bob instead (without the single quotes).
You are defining a predicate and you forget to use one of the variables in it. You either have to make it an anonymous variable, _Bob, if you really don't care about it, or you find where in the predicate you were supposed to use it.

Take list as input from user, and use it in other predicates like append, and some other which I want to implement a code

test():-
write("list1"),
read(A),
write("list2"),
read(B),
write(A),
write(B).
append([],X,X).
append([X|Y],Z,[X|W]) :- append(Y,Z,W).'
The output of the code is:
?- test().
list1[A,B,C].
list2|: [D,E].
[_3842,_3848,_3854][_3866,_3872]
true.
But I want it to be as normal Alphabets.
The read predicate is intended for reading terms. For reading strings, use read_string instead.

Array Univ var ([x,y]=..T) - prolog

I saw a question asking what does [a,b,c]=..L. return.
When testing this I saw that it returns: L = ['.', a, [b, c]].
I can't understand why this happens, I was unable to understand the nature of Univ from the documentation. Understanding this will help me understand Univ.
One way to learn more about terms is to use write_canonical/1 in a conforming Prolog system.
For example, with GNU Prolog, we obtain:
| ?- write_canonical([x,y]).
'.'(x,'.'(y,[]))
This shows:
the primary functor in this term is '.', with arity 2
the first argument is x
the second argument is '.'(y, []), which is the list [y]
This explains why (=..)/2 yields:
| ?- [x,y] =.. Ls.
Ls = ['.',x,[y]]
and also your other example.
This happends because representation of the list in prolog is a tree datastructure,like this.It's top node is a "dot" left side is Head then again a dot on right if tail is not empty and head on left hand side and "dot" on right handside. When you do this you are simply creating a predicate(well , not exact a predicate but it is sometimes needed as i show an example): suppose i write:
V=..[somefunctor,X,Y,Z]
Then it will automatically construct a predicate like this:
somefunctor(X,Y,Z).
Now Why do we need this? Supppose i call a predicate with these terms: predicate(somefunctor,term,term2,term3) and predicate or rule looks something like this: predicate(X,Y,Z,T) and i ask you that no matter what predicate is in X, you have to call this predicate with parameters Y,Z,T. May be you think you call that predicate by writing like this: X(Y,Z,T) but unfortunately it is not allowed in prolog, so here you can use V=..[X,Y,Z,T] where X should be placed as first argument because it's predicate name and as a result you get something like this: V = somefunctor(term,term2,term3) and this happends internally. In order to invoke this predicate you make use of call predicate:
call(V) where `call/1` is a metapredicate and `V=..` is a not logical predicate.

Resources