我正在嘗試在 Prolog 中撰寫一條規則,該規則將首先檢查第二個串列中的所有元素是否包含在第一個串列中,以及第二個串列中的所有元素是否都是偶數。
因此,例如以下查詢:
evenSubList([5, 6, 7, 8], [6, 8]). -> True
evenSubList([5, 6, 7, 8], [6, 7, 8]). -> no
evenSubList([5, 6, 7, 8], X). -> X = [6, 8]
evenSubList([6, 7, 8], [6, 8]). -> True
evenSubList([6, 8], [6, 8]). -> True
當我查詢我當前的代碼時,它只有在兩個串列都只有偶數時才有效。第一個串列不允許有任何奇數。我也嘗試過使用內置的子串列規則,但沒有成功。我知道問題出在我的第二個定義中,兩個串列中的頭部不同,但我不確定我做錯了什么。
evenSubList([X | _], [X]) :- % base case gets hit if second list only has one element
mod(X, 2) =:= 0.
evenSubList([X | Y], [Z | T]) :- % If first element of both lists are different
evenSubList(Y, [Z]),
evenSubList(Y, T).
evenSubList([X | Y], [X | Z]) :- % If both heads are the same
mod(X, 2) =:= 0,
evenSubList(Y, Z).
uj5u.com熱心網友回復:
您的想法是正確的,只是您的頭部不一樣,您嘗試一次做兩件事并絆倒自己,因為最終,您將有一個空串列,并且將回傳 false。有一個更簡單的解決方案。
您從尾部開始Y,然后遍歷將其與頭部進行比較Z,但如果遇到兩個頭部相同的情況,您將有一個空呼叫,這將導致輸出為no.
在您的第二次遞回呼叫中evenSubList(Y, T),如果T比 短Y,您將遇到空串列問題。
您想做這樣的事情,其中??第一個串列變小,第二個串列保持相同大小,并將第一個串列中的每個元素與第二個串列作為一個整體進行比較,直到或除非遇到其他情況才會改變你會知道在第二個串列的尾部是安全的。
evenSubList([X], [X]) :-
mod(X, 2) =:= 0.
evenSubList([X | Y], [X | Z]) :-
mod(X, 2) =:= 0,
filterevens(Y, Z).
evenSubList([X | Y], [Z | T]) :-
evenSubList(Y, [Z | T]).
uj5u.com熱心網友回復:
這很簡單:
even_contains(LstFull, LstEven) :-
include(is_even, LstFull, LstEven).
is_even(N) :-
0 is N mod 2.
結果 swi-prolog:
?- even_contains([5, 6, 7, 8], [6, 8]).
true.
?- even_contains([5, 6, 7, 8], [6, 7, 8]).
false.
?- even_contains([5, 6, 7, 8], X).
X = [6,8].
?- even_contains([6, 7, 8], [6, 8]).
true.
?- even_contains([6, 8], [6, 8]).
true.
轉載請註明出處,本文鏈接:https://www.uj5u.com/qukuanlian/448931.html
