我现在被困在这个问题上2个小时了!我在prolog中的问题是我以一种声明的方式思考! 所以我的问题是让prolog生成一个等于N的列表!列表的大小为5。
somme([],0) :- !.
somme([X|L],S) :- somme(L,S1), S is S1+X.
generateList(L,RES) :- C1 is random(4)+1,
C2 is random(5)+1,
C3 is random(6)+1,
append(L,[C1,C2,C3],RES).
go(L) :- generateList([2,3],L), somme(L,S), S \==16, go(L).
go(L) :- generateList([2,3],L), somme(L,S), S == 16,write(L).
我们假设第一个元素是2和3。
答案 0 :(得分:4)
您也可以使用CLP(FD)来描述此类列表:
:- use_module(library(clpfd)).
numbers(L) :-
L=[2,3,_A,_B,_C], % list has 5 elements and begins with 2,3
L ins 0..16, % the list elements are between 0 and 16
sum(L, #=, 16). % the sum of the list elements is 16
如果您查询此谓词,则会将剩余目标作为答案,因为谓词没有唯一的解决方案:
?- numbers(L).
L = [2,3,_A,_B,_C],
_A in 0..11,
_A+_B+_C#=11,
_B in 0..11,
_C in 0..11
在查询中添加label / 1,您将获得所有78个解决方案:
?- numbers(L), label(L).
L = [2,3,0,0,11] ? ;
L = [2,3,0,1,10] ? ;
L = [2,3,0,2,9] ? ;
...
您可以使用bagof / 3收集所有解决方案,如下所示:
?- bagof(L,(numbers(L), label(L)),Xs).
Xs = [[2,3,0,0,11],[2,3,0,1,10],[2,3,0,2,9],[2,3,0,3,8],[2,3,0,4,7],[2,3,0,5,6],[2,3,0,6,5],[2,3,0,7,4],[2,3,0,8,3],[2,3,0,9,2],[2,3,0,10,1],[2,3,0,11,0],[2,3,1,0,10],[2,3,1,1,9],[2,3,1,2,8],[2,3,1,3,7],[2,3,1,4,6],[2,3,1,5,5],[2,3,1,6,4],[2,3,1,7,3],[2,3,1,8,2],[2,3,1,9,1],[2,3,1,10,0],[2,3,2,0,9],[2,3,2,1,8],[2,3,2,2,7],[2,3,2,3,6],[2,3,2,4,5],[2,3,2,5,4],[2,3,2,6,3],[2,3,2,7,2],[2,3,2,8,1],[2,3,2,9,0],[2,3,3,0,8],[2,3,3,1,7],[2,3,3,2,6],[2,3,3,3,5],[2,3,3,4,4],[2,3,3,5,3],[2,3,3,6,2],[2,3,3,7,1],[2,3,3,8,0],[2,3,4,0,7],[2,3,4,1,6],[2,3,4,2,5],[2,3,4,3,4],[2,3,4,4,3],[2,3,4,5,2],[2,3,4,6,1],[2,3,4,7,0],[2,3,5,0,6],[2,3,5,1,5],[2,3,5,2,4],[2,3,5,3,3],[2,3,5,4,2],[2,3,5,5,1],[2,3,5,6,0],[2,3,6,0,5],[2,3,6,1,4],[2,3,6,2,3],[2,3,6,3,2],[2,3,6,4,1],[2,3,6,5,0],[2,3,7,0,4],[2,3,7,1,3],[2,3,7,2,2],[2,3,7,3,1],[2,3,7,4,0],[2,3,8,0,3],[2,3,8,1,2],[2,3,8,2,1],[2,3,8,3,0],[2,3,9,0,2],[2,3,9,1,1],[2,3,9,2,0],[2,3,10,0,1],[2,3,10,1,0],[2,3,11,0,0]]
如果有额外的目标长度/ 2,您可以计算收集的解决方案的数量:
?- bagof(L,(numbers(L), label(L)),Xs), length(Xs,Len).
Len = 78,
Xs = [[2,3,0,0,11],[2,3,0,1,10],[2,3,0,2,9],[2,3,0,3,8],[2,3,0,4,7],[2,3,0,5,6],[2,3,0,6,5],[2,3,0,7,4],[2,3,0,8,3],[2,3,0,9,2],[2,3,0,10,1],[2,3,0,11,0],[2,3,1,0,10],[2,3,1,1,9],[2,3,1,2,8],[2,3,1,3,7],[2,3,1,4,6],[2,3,1,5,5],[2,3,1,6,4],[2,3,1,7,3],[2,3,1,8,2],[2,3,1,9,1],[2,3,1,10,0],[2,3,2,0,9],[2,3,2,1,8],[2,3,2,2,7],[2,3,2,3,6],[2,3,2,4,5],[2,3,2,5,4],[2,3,2,6,3],[2,3,2,7,2],[2,3,2,8,1],[2,3,2,9,0],[2,3,3,0,8],[2,3,3,1,7],[2,3,3,2,6],[2,3,3,3,5],[2,3,3,4,4],[2,3,3,5,3],[2,3,3,6,2],[2,3,3,7,1],[2,3,3,8,0],[2,3,4,0,7],[2,3,4,1,6],[2,3,4,2,5],[2,3,4,3,4],[2,3,4,4,3],[2,3,4,5,2],[2,3,4,6,1],[2,3,4,7,0],[2,3,5,0,6],[2,3,5,1,5],[2,3,5,2,4],[2,3,5,3,3],[2,3,5,4,2],[2,3,5,5,1],[2,3,5,6,0],[2,3,6,0,5],[2,3,6,1,4],[2,3,6,2,3],[2,3,6,3,2],[2,3,6,4,1],[2,3,6,5,0],[2,3,7,0,4],[2,3,7,1,3],[2,3,7,2,2],[2,3,7,3,1],[2,3,7,4,0],[2,3,8,0,3],[2,3,8,1,2],[2,3,8,2,1],[2,3,8,3,0],[2,3,9,0,2],[2,3,9,1,1],[2,3,9,2,0],[2,3,10,0,1],[2,3,10,1,0],[2,3,11,0,0]]
答案 1 :(得分:1)
你的计划,修改过:
somme([],0). /* the cut is useless, since [] and [X|L] are distinguished */
somme([X|L],S) :- somme(L,S1), S is S1+X.
generateList(L,RES) :- C1 is random(4)+1,
C2 is random(5)+1,
C3 is random(6)+1,
append(L,[C1,C2,C3],RES).
/* A variable can be assigned only once, then you must backtrack. */
/* So: repeat/0 introduces a backtrack point, going into a "failure driven loop" */
/* until the test succeeds */
go(L) :- repeat, generateList([2,3],L), somme(L,S), S == 16, !.
试运行
?- go(L).
L = [2, 3, 2, 4, 5].
?- go(L).
L = [2, 3, 2, 3, 6].