说我有以下理论:
a(X) :- \+ b(X).
b(X) :- \+ c(X).
c(a).
Run Code Online (Sandbox Code Playgroud)
它只是说真的,这当然是正确的,a(X)因为没有b(X)(因为有限的失败否定).因为只有一个b(X)如果没有c(X),我们就有c(a),可以说这是真的.我想知道为什么Prolog没有提供答案X = a?比如说我介绍一些语义:
noOrphan(X) :- \+ orphan(X).
orphan(X) :- \+ parent(_,X).
parent(david,michael).
Run Code Online (Sandbox Code Playgroud)
当然,如果我查询noOrphan(michael),这将导致true与noOrphan(david)在false(因为我没有定义父david),但我不知道为什么会有的检测没有积极主动地哪些人(michael,david,...)属于noOrphan/1关系?
这可能是Prolog的回溯机制的结果,但是Prolog可以维持一个状态,该状态验证一个人是否以积极方式(0,2,4,...)否定深度或负面方式(1,3) ,5,...)否定深刻.
让我们从更简单的事情开始吧.说\+ X = Y.这里,否定的目标是预定义的内置谓词.因此,事情更清楚:X与Y应有所不同.然而,\+ X = Y失败,因为X = Y成功.因此,没有任何痕迹留在目标失败的精确条件下.
因此,\+ \+ X = Y确实产生一个空的答案,而不是预期的答案X = Y.看到这个答案更多.
鉴于这些简单的查询已经显示出问题,您不能期望过多的用户定义目标,例如您的目标.
在一般情况下,您必须首先重新考虑否定的实际含义.答案比初看起来要复杂得多.想想该计划p :- \+ p.应该p成功还是失败?应该p是真的吗?实际上有两种模型不再符合Prolog关于使用最小模型的观点.这些考虑为逻辑编程开辟了新的分支,如答案集编程(ASP).
但是,让我们坚持Prolog.否定只能在非常有限的上下文中使用,例如当目标被充分实例化并且定义被分层时.不幸的是,没有普遍接受的安全执行否定目标的标准.我们可以等到目标变量自由(地面),但这通常意味着我们必须等待太长时间 - 用行话:否定的目标比目鱼.
如此有效,一般否定与纯Prolog程序并不完美.Prolog的核心确实是该语言的纯粹,单调的子集.然而,在Prolog(或其各自的扩展)的约束部分中,否定可能会很好地起作用.
| 归档时间: |
|
| 查看次数: |
832 次 |
| 最近记录: |