【发布时间】:2020-06-26 00:56:29
【问题描述】:
如果or 运算符两侧的两条规则中的任何一条在 Prolog 中成功,我将尝试返回 true。仅当发现 or 运算符左侧的内容为 true 时才有效。
看来我的代码应该按照http://www.cse.unsw.edu.au/~billw/dictionaries/prolog/or.html 工作。
Case2 在case1 被注释掉时有效,所以它应该返回true,但因为它在运算符的右侧,所以它不是。 (?)
为清楚起见,参数表示Person1、Person2、TypeOfCousinsTheyAre、DegreesRemovedTheyAre。我正在尝试编写规则来确定两个人是否被一次性移除。
这是使用or 运算符的行,如果右侧为真,则不会返回true:
cousins(A, B, 1, 1) :- ( cousinsCase1(A, B, 1, 1) ; cousinsCase2(A, B, 1, 1) ).
我尝试过的其他事情:
(1) 省略or 运算符并编写两个相同的函数,但每当调用它们并且顶部的函数失败时,我的程序就会崩溃。
cousins(A, B, 1, 1) :- var(FirstCousin),
cousin(A, FirstCousin, 1, 0),
parent(FirstCousin, B),
A \= B.
cousins(A, B, 1, 1) :- var(P1),
parent(P1, A),
cousin(P1, B, 1, 0),
A \= B,
A \= P1,
B \= P1.
(2) 我也尝试过if-statement 来在第一个失败时调用另一个函数,但如果第一个案例再次失败,它会崩溃。
cousins(A, B, 1, 1) :- cousinsCase1(A, B, 1, 1) -> true ; cousinsCase2(A, B, 1, 1)).
如果第一个规则失败,是否有其他方法可以调用另一个规则?
编辑
根据给出的建议,这里有更多代码:
事实:
parent(gggm, ggm).
parent(ggm, gm).
parent(gm, m).
parent(m, self).
parent(self, d).
parent(d, gd).
parent(gggm, gga).
parent(gga, c12a).
parent(c12a, c21a).
parent(c21a, c3).
parent(ggm, ga)
parent(ga, c11a).
parent(c11a, c2).
parent(gm, a).
parent(a, c1).
parent(m, s).
parent(s, n).
parent(n, gn).
parent(c1, c11b).
parent(c11b, c12b).
parent(c2, c21b).
parent(c21b, c22).
parent(c3, c31).
parent(c31, c32).
我为使上述规则生效而编写的其他规则:
% Sibling Rule
sibling(A, B) :- parent(P, A), parent(P, B), A \= B.
% First-cousin Rule:
cousin(A, B, 1, 0) :- sibling(P1, P2), parent(P1, A), parent(P2, B).
% Second-cousin Rule:
cousin(A, B, 2, 0) :- parent(P1, A),
parent(P2, B),
parent(PP1, P1), % your grandparent
parent(PP2, P2), % your grand-aunt/uncle
sibling(PP1, PP2). % they're siblings
% 3rd-cousin and more Rule
cousin(A, B, M, 0) :- ReducedM = M - 1,
cousin(A, B, ReducedM, 0).
调用上述规则:旁注:两个调用都可以工作,但问题是让它们都工作而没有注释掉另一个规则:
表兄弟(self, c11b, 1, 1)。
此调用对应于第一个“1st-cousin, once-removed”案例,如果其他案例被注释掉,则该案例返回正确答案 true。
堂兄弟(self, c11a, 1, 1)。
此调用对应于第二个“1st-cousin, once-removed”案例,如果另一个案例被注释掉,则该案例返回正确答案 true。
【问题讨论】:
-
问题显然出在代码的其他地方。 minimal reproducible example 可以澄清这里的事情......一次只关注一个错误。
-
在
cousins/2谓词的两个子句中,目标var(FirstCousin)和var(P1)总是为真,因为它们是子句正文中的第一个目标,而参数不是子句头部的变量。 -
我正在考虑回答这个问题,但问题是我必须从头开始创作这么多的作品,因为你没有包含它,我不是在帮助你学习,而只是给你答案。我什至不知道你谓词中的数字是什么意思,代表人们关系的事实在哪里?
-
另一件可以帮助您解决问题的方法是使用测试用例。我目前的信念是您的表亲/ 4 谓词中的一个或两个是错误的。如果您有测试用例并分别测试每个用例,那么您将知道是否是那些谓词抛出了逻辑。仅仅因为你学会了使用 ;/2 并不意味着你用错了,这是你应该关注的。但正如我所指出的,您在问题中遗漏了很多内容,我只能猜测。
-
感兴趣的:Cousin tree
标签: prolog or-operator