【问题标题】:Optimising a Prolog Rule优化 Prolog 规则
【发布时间】:2021-03-04 22:44:22
【问题描述】:

我有以下 Prolog 规则:

p(X,Y):- q(Y,X), r(Y), s(Y), t(X).

已知r(Y)s(Y)只有一种解,而q(X,Y)p(X,Y)有几种解。

任务是使用辅助谓词优化规则。

我的猜测是在 s(Y)t(X) 之间放置一个 Cut 以防止无用的回溯。

可以写什么样的辅助谓词来优化这条规则?

【问题讨论】:

    标签: prolog


    【解决方案1】:

    小心剪裁。例如,如果 - 在您的第一次尝试中 - 您选择了正确的 Y,但错误的 X(对于 t(X))在谓词正文中使用剪切将提供错误的答案。

    例子:

    r(1).
    s(1).
    t(X):- member(X,[7,8,9,6]).
    q(Y,X):- member(X,[1,2,3,6]), member(Y,[3,4,5,6,1]).
    
    p(X,Y):- q(Y,X), r(Y), s(Y), t(X).
    
    ?- p(X,Y).
    X = 6,
    Y = 1.
    

    但是有

    p(X,Y):- q(Y,X), r(Y), s(Y), !, t(X).
    
    ?- p(X,Y).
    false.
    

    如果您在 aux 谓词中使用剪切,剪切不会丢弃“正确”答案,因为即使 aux/2 被传递一次,在预测 p/2 中仍然允许回溯:

    aux(Y) :- r(Y), s(Y), !.
    p(X,Y):- q(Y,X), aux(Y), t(X).
    
    ?- p(X,Y).
    X = 6,
    Y = 1.
    

    我刚刚看到使用 aux 谓词没有任何改进。但是使用

    aux(Y) :- r(Y), !, s(Y).
    

    aux(Y) :- !, r(Y), s(Y).
    

    如果s/1 计算成本高,可能会提高速度。只有在之前实例化了 Y 时才应使用第二种解决方案。此外,对谓词重新排序可能会加快速度。

    【讨论】:

    • 那么我是否理解正确,aux/1 中间的剪辑阻止了子目标 s(Y) 的进一步回溯,一旦 r(Y) 评估为真?并且aux/1 不会阻止p(X,Y) 中的回溯?
    • @gython 正确。剪切仅适用于当前谓词。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-01-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多