【问题标题】:Outputting final list from recursive predicate in Prolog从 Prolog 中的递归谓词输出最终列表
【发布时间】:2014-02-03 23:36:04
【问题描述】:

我写了一个程序,它在 Prolog 列表中找到最长的互质子序列(它还没有完美):

longest_lcs([A, B | Tail],X) :- gcd(A,B,1),lcs([B | Tail],X,A,1).
longest_lcs([A, B | Tail],X) :- lcs([B | Tail],X,A,0).

lcs([],G,_,_) :- rev(G,G1),write(G1).

lcs([A, B | Tail],G,Q,_) :- gcd(B,Q,1), gcd(A,B,1), lcs([B | Tail], [Q | G], A, 1),!.
lcs([A, B | Tail],G,Q,_) :- gcd(B,Q,1);gcd(A,B,1), lcs([B | Tail], [Q | G], A, 0).

lcs([A, B | Tail],G,_,0) :- gcd(A,B,1), lcs([B | Tail], G, A, 1).
lcs([A, B | Tail],G,_,1) :- lcs([B | Tail], G, A, 1).
lcs([A, B | Tail],G,_,0) :- lcs([B | Tail], G, A, 0).

lcs([A],G,Q,_) :- gcd(Q,A,1),lcs([], [A, Q | G], _, _).    

目前我输出带有write谓词的子序列,但我需要它以以下方式运行:

?- longest_lcs([1,2,3,4],X).
X = [1,2,3,4]

?- longest_lcs([2,4,8,16],X).
X = []

我需要进行哪些修改,这样才有效?

【问题讨论】:

    标签: list prolog


    【解决方案1】:

    为什么要使用 write/1?专注于对您想要的内容进行清晰的声明性描述,顶层将为您完成写作。最长互质子序列的可能公式是:它是互质子序列,并且没有其他互质子序列更长。代码可能类似于:

    list_lcpsubseq(Ls, Subseq) :-
        list_subseq(Ls, Subseq),
        coprimes(Subseq),
        length(Subseq, L),
        \+ ( list_subseq(Ls, Others), coprimes(Others), length(Others, O), O > L ).
    

    【讨论】:

    • write/1 是调试算法的临时解决方案。这个解决方案的问题(乍一看)是它不会在多项式时间内运行。
    • 是否存在多项式时间算法的承诺?在我看来,最大长度互质子序列是节点上图的最大团,其中边表示两个整数的互质性。 mat 的代码清晰正确(给定辅助谓词的适当实现)。如果效率是一个真正的目标(家庭作业并非总是如此),那么我宁愿从完善 mat 的实现开始,而不是完善你的实现。
    猜你喜欢
    • 2018-10-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多