Prolog Assigning integer to a variable

穿精又带淫゛_ 提交于 2020-02-05 08:38:35

问题


I'm new to Prolog, and using GNU Prolog, so no clp(fd) allowed. What I'm trying to do is for a given integer N, generate a list with elements of 1 ~ N. So set(3,T). will output T = [1,2,3]. Here is what I have so far:

set(0,[]).
set(N,T):-set(N-1,T1),append(T1,[N],T).

When I try set(2,T), it crashes. I debugged with trace, and find out that it's not evaluating N-1, but rather doing N-1-1-1...

Anyone can tell me how to solve this? Thank you.


回答1:


It should be:

set(N,T):- N2 is N-1, set(N2,T1), append(T1,[N],T).

Arithmetic operations are performed by using is/2. N-1 is a shorthand for -(N,1) (just like N2 is N-1 is shorthand for is(N2, N-1)), so you were just creating infinite tree -(-(-(-(...),1),1,1,1).

Little educational note:

If you want set/2 to be proper relation so it can answer queries like set(3,X), set(X, [1,2,3]) and set(X,Y) without error then you should write this predicate that way:

set(0, []).
set(Value, List) :-
  length(List, Value),
  append(ShorterList, [Value], List),
  ValueMinusOne is Value - 1,
  set(ValueMinusOne, ShorterList).

That way result of arithmetic operation is always possible to obtain because input value (lenght of the list) is either explicitly given or generated from length/1.




回答2:


n_ups(N, Xs) :-
   length(Xs, N),
   numbered_from(Xs, 1).

numbered_from([], _).
numbered_from([I0|Is], I0) :-
   I1 is I0+1,
   numbered_from(Is, I1).

In fact, the complexity is hidden within length/2.



来源:https://stackoverflow.com/questions/23261379/prolog-assigning-integer-to-a-variable

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!