我试图整理一个Prolog程序,它将接收一个数字和一个输出列表,并基本上列出[I,J]形式的列表,其中I + J = N.这里&#39 ;我的代码,输出我得到:
loop(I, J, [[X,Y]|Lout]):-
I > 0,
I1 is I-1,
J1 is J+1,
X is I1,
Y is J1,
loop(I1, J1, Lout).
loop(I, J, [[I,J]]).
listFromLoop(N, W):-
loop(N,0,W).
输出:
?- listFromLoop(4,W).
W = [[3, 1], [2, 2], [1, 3], [0, 4], [0, 4]] ;
W = [[3, 1], [2, 2], [1, 3], [1, 3]] ;
W = [[3, 1], [2, 2], [2, 2]] ;
W = [[3, 1], [3, 1]] ;
W = [[4, 0]].
我在最后得到两个额外的元素([0,4],[0,4]),我不需要,以及必须逐步完成它,而不是全部显示为单个列表。
这是它应该是什么样子:
?- listFromLoop(4,W).
W = [[3, 1], [2, 2], [1, 3]].
我很接近,但我认为我的主要问题是我试图像C ++或Java while循环那样编写代码。但是,在Prolog中,这似乎不是正确的方法。
非常感谢任何帮助!
修改
我明白了!经过一点点阅读后,似乎我错过了递归版本的基本情况。以下是我最终解决的问题。虽然,我不确定这是否是在Prolog中执行此操作的正确/最有效的方法。
loop(1,_,[]):- !.
loop(I, J, [[X,Y]|Lout]):-
I > 0,
I1 is I-1,
J1 is J+1,
X is I1,
Y is J1,
loop(I1, J1, Lout).
listFromLoop(N, W):-
loop(N,0,W).
答案 0 :(得分:0)
你的代码很好,但是我会做一些清理它的事情:
while True:
line = input('Enter the GNSS message')
print(line)
if line == 'done':
break
GNSS_data = line.split(" ")
print("Timezone: {}".format(GNSS_data[-1]))
print("Time: {}".format(GNSS_data[-2]))
print("Date = {}".format(GNSS_data[-3]))
print("\n")
你并没有真正使用循环 - 它是构建列表的递归。所以只需称它为build(1, _, []).
build(I, J, [[X, Y]|Zs]) :-
I > 1,
X is I - 1,
Y is J + 1,
build(X, Y, Zs).
build(N, W) :- build(N, 0, W).
。定义具有相同名称但不同数量的参数的谓词也是完美的。
我还将build
命名为Lout
,因为这有助于表明它是一个列表 - prolog通常不关心输入或输出。您可以运行查询Zs
,即使您已将输出列表作为输入参数发送,也会获得成功。
答案 1 :(得分:0)
更惯用的方式:
listFromLoop(U,W) :- U_ is U-1,
findall([I,J],(between(1,U_,J),I is U_-J+1),W).