2011-06-08 74 views
0

嗨,大家好,我是Prolog的新手。 我試圖在第3課中結合1000個元素而不重複。 我已經做了代碼,但我有堆棧問題。Prolog跳出全球堆棧

member(T, [T|R], R) :- !. 
member(T, [_|L], R) :- member(T, L, R). 

last_element([H], H) :- !. 
last_element([H|[X]], X) :- !. 
last_element([H|T], R) :- last_element(T, R). 


    macronutrienti(1). 
    macronutrienti(2). 
    macronutrienti(3). 
    and so on 

percentuale_macronutrienti(Alimento, R) :- 
    macronutrienti(Alimento), 
    R = Alimento. 

combina(NRAlimenti, RIS) :- 
    findall(PM, percentuale_macronutrienti(Alimento, PM), PMR), 
    f1(NRAlimenti, PMR, PMR, RIS), !. 

f1(1, RParz, PMR, RParz) :- !. 
f1(Index, RParz, PMR, RIS) :- 
    Index1 is Index - 1, 
    g2(RParz, PMR, RIS1, RIS1), 
    f1(Index1, RIS1, PMR, RIS). 
f1(Index, RParz, PMR, RIS) :- 
    Index1 is Index - 1, 
    g1(RParz, PMR, RIS1, RIS1), 
    f1(Index1, RIS1, PMR, RIS). 

g1([A|[TA]], A1, OldR, R) :- 
    q([A], L1, A1), 
    h1(A, L1, OldR, OldR), !. 
g1([A|T], A1, Risultato, R) :- 
    q([A], L1, A1), 
    h1(A, L1, OldR, OldR), 
    append(OldR, TOldR,Risultato), 
    g1(T, A1, TOldR, R). 

q(A, R, A1) :- last_element(A, LastElement), member(LastElement, A1, R). 

g2([A|[TA]], A1, OldR, R) :- 
    q(A, L1, A1), 
    h2(A, L1, OldR, OldR), !. 
g2([A|T], A1, Risultato, R) :- 
    q(A, L1, A1), 
    h2(A, L1, OldR, OldR), 
    append(OldR, TOldR, Risultato), 
    g2(T, A1, TOldR, R). 

h1(_, [], _, _) :- !. 
h1(Alimento, [Alimento1], [OldM], R) :- append([Alimento], [Alimento1], OldM). 
h1(Alimento, [Alimento1|T1], [OldM|TOldM], NewM) :- 
    append([Alimento], [Alimento1], OldM), 
    h1(Alimento, T1, TOldM, NewM). 

h2(_, [], _, _) :- !. 
h2(Alimento, [Alimento1], [OldM], R) :- append(Alimento, [Alimento1], OldM). 
h2(Alimento, [Alimento1|T1], [OldM|TOldM], NewM) :- 
    append(Alimento, [Alimento1], OldM), 
    h2(Alimento, T1, TOldM, NewM). 

:- combinew(3,R). 

出了什麼問題?謝謝你在前進

+0

可能prolog卡在某種無限循環或搜索。使用trace來檢查prolog試圖找到解決方案的方式。 – 2011-06-08 21:40:06

+0

相同的代碼工作爲400 macronutrienti(n),但如果我插入1000 macronutrienti(n),prolog走出堆棧。問題不是無限循環,但我認爲是遞歸調用的數量。 – 2011-06-09 14:08:28

+0

在這種情況下,您可以嘗試擴展堆棧:http://www.swi-prolog.org/pldoc/doc_for?object=set_prolog_stack/2 – 2011-06-09 21:04:08

回答

0

這裏有一個更短的代碼,(我認爲)不一樣的你:

combine(N,L) :- 
    findall(PM, macronutrienti(PM), PMR), 
    findall(L0, combine0(N, PMR, L0), LL). 

combine0(0, _, []) :- !. 
combine0(I, PMR, [X|LR]) :- 
    member(X, PMR, PMRR), 
    I1 is I-1, 
    combine0(I1, PMRR, LR). 

member(T, [T|R], R). 
member(T, [_|L], R) :- member(T, L, R). 

(我稍微改變你的member/3謂語)

然而,這仍然不能解決你的堆棧溢出問題。基本上,如果我正確理解你的問題,你想從1000個元素集合中提取長度爲3的所有排序子集。您正在查看的套數是1000!/(1000-3)!,即長度爲3的997.002.000列表。這非常多,所以如果您需要巨大的堆棧。

如果您不需要完整的列表來繼續,請更改您的工作流程以一次生成一個此類項目,然後立即處理它,然後繼續下一個。