Prolog查询中带有变量的"\ +"问题 [英] Problem with `\+` in Prolog queries with variables

查看:452
本文介绍了Prolog查询中带有变量的"\ +"问题的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在阅读七个星期内可以使用七种语言"自动取款机,并且遇到了一些Prolog查询,但我不理解对此的否定答复.

I'm reading "Seven languages in seven weeks" atm, and I'm stumped over some Prolog query that I don't understand the 'no' response to.

friends.pl文件如下所示:

likes(wallace, cheese).
likes(grommit, cheese).
likes(wendolene, sheep).

friend(X, Y) :- \+(X = Y), likes(X, Z), likes(Y, Z).

我可以对其进行一些琐碎的查询,例如:

I can do some trivial queries on it, such as:

| ?- ['friends'].
compiling /home/marc/btlang-code/code/prolog/friends.pl for byte code...
/home/marc/btlang-code/code/prolog/friends.pl compiled, 12 lines read - 994 bytes written, 8 ms

yes
| ?- friend(wallace,grommit).

yes
| ?- friend(wallace,wendolene).

no

这一切都符合预期.现在,我想在查询中引入一个变量.我的目的是让Prolog列出所有Wallace朋友的清单.我期待X = grommit,但我得到no:

This is all as expected. Now, I want to introduce a variable in the query. My intent being that Prolog will give me a list of all of Wallace's friends. I'm expecting X = grommit, but I'm getting no:

| ?- trace.
The debugger will first creep -- showing everything (trace)

yes
{trace}
| ?- friend(wallace,X).
      1    1  Call: friend(wallace,_16) ?
      2    2  Call: \+wallace=_16 ?
      3    3  Call: wallace=_16 ?
      3    3  Exit: wallace=wallace ?
      2    2  Fail: \+wallace=_16 ?
      1    1  Fail: friend(wallace,_16) ?

no
{trace}

它甚至没有尝试将X(_16)与grommit统一.为什么?

It doesn't even try to unify X (_16) with grommit. Why?

推荐答案

是朋友的定义:

friend(X, Y) :- \+(X = Y), likes(X, Z), likes(Y, Z).

这里重要的是,您从\+(X = Y)开始,通常将其定义为:

The important thing here is that you start with \+(X = Y) which is normally defined as:

\+ Goal :- Goal,!,fail

请注意,这意味着如果目标成功,您肯定会失败.可用变量(尚未分配的变量)将始终统一,因此是相等的,因此您总是会因使用可用变量而失败.因此,如果尚未为X或Y赋值,则永远不会为它赋值.

Note that this means that if goal succeeds, you are sure to fail. Free variables (ones that havent been assigned) will always unify, and thus be equal, so you will always fail with a free variable. It will thus never assign a value to X or Y if it doesn't already have one.

相反

friend(X, Y) :-  likes(X, Z), likes(Y, Z), \+(X = Y)

将表现出更多预期.

这里的问题是,序言为您提供了控制程序流的强大方法,但实际上并不能很好地适应其更加面向逻辑的设计.应该以不产生这些问题的方式来表达否定为失败"类型的约束.因此,我不是Prolog的忠实拥护者.

The problem here is that prolog gives you powerful ways to control the flow of programs, but those dont really fit nicely with its more logic oriented design. It should be possible to express "negation as failure" type constraints in a way that does not produce these problems. I'm not a huge prolog fan for this reason.

这篇关于Prolog查询中带有变量的"\ +"问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆