2017-07-07 90 views
2

我被困在這個問題2個小時了!我在序言中的問題是我在用聲明的方式思考!
所以我的問題是讓prolog生成一個等於N的列表!列表的大小爲5列表總和必須是16

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第一個元素是2和3

+0

您的意思是在Prolog中以聲明方式思考。所以這不是問題。 – Enigmativity

回答

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]. 
+0

謝謝。你拯救了我的一天。沒有使用重複的另一種解決方案? –

+0

因爲如果我想顯示所有的結果我能在這種情況下做什麼? –

+0

首先,不要使用隨機/ 1,而應該使用確定性生成器,比如介於/ 3之間。否則 - 我認爲 - 有沒有簡單的方法來打破*無限*生成過程 – CapelliC

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 

添加標籤/ 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]] 
相關問題