prolog - 在 Prolog 中表达 "Commutativity"的替代方法?

标签 prolog commutativity

作为 Prolog 的初学者,我发现 Prolog 中的交换表达式很不直观。

例如,如果我想表达 X 和 Y 在一个家庭中,例如:

family(X,Y) :-
      married(X,Y);
      relative(X,Y);
      father_son(X,Y).

我还应该在定义中添加以下内容,以使其“可交换”:
      married(Y,X);
      relative(Y,X);
      father_son(Y,X).

但是我们使用Prolog,因为我们想编写优雅的代码......所以,我希望在原始代码中只添加一行(而不是上面的三行):
      family(Y,X).

这是要点。它会导致终止!为什么序言没有那么“合乎逻辑”?是否有替代这种不会导致终止的简洁的单行表达式?

周末愉快!

最佳答案

family(X,Y) :- family(Y,X). 的问题规则的一部分是它在每个级别都无条件地与自己统一,并不断向下递归;这个递归没有退出条件。

您应该在上面的级别进行参数交换:

family(X,Y) :-
    is_family(X,Y);
    is_family(Y,X).

is_family(X,Y) :-
    married(X,Y);
    relative(X,Y);
    father_son(X,Y).

或者,您可以在有意义的地方制定低于对称的基础规则:
is_married(X,Y) :-
    married(X,Y);
    married(Y,X).

is_relative(X,Y) :-
    relative(X,Y);
    relative(Y,X).

您现在可以重写您的 family规则如下:
family(X,Y) :-
    is_married(X,Y);
    is_relative(X,Y);
    father_son(X,Y);
    father_son(Y,X).

关于prolog - 在 Prolog 中表达 "Commutativity"的替代方法?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10257947/

相关文章:

javascript - 乘法不是可交换的?

python - 来自 Pandas 的 groupby 是可交换的吗?

prolog - 如何使用成员谓词在序言中指定约束

prolog - 在到达预期节点之前,如何知道图中的所有节点是否已被访问?

prolog - 所有可达节点的祖先

prolog - 有没有可以绘制 Prolog 查询的搜索树的程序?

proof - Agda 重写不会改变 _*_ 交换性证明中的目标

postgresql - 内连接sql的结合性和交换性

regex - 正则表达式匹配序言

rust - 需要 Rust 特征边界中的交换操作