prolog中的单例变量

时间:2013-03-14 17:31:40

标签: prolog

我正在测试我的新版SWI prolog并不断遇到错误:单例变量

示例:

member(X,[X|T]).

member(X,[X|T]) :- member(X,T).

找到列表的成员,例如:

member(yolands,[yolanda,tim])

X = yes

但是我得到X和T的单例变量错误

如果我执行以下操作:

member(X,[X|_]).
member(X,[_|T]) :- member(X,T).

它有效,但看起来很难看!

任何人都可以解释为什么允许单个变量和这个ANSI标准?

3 个答案:

答案 0 :(得分:15)

单个变量在Prolog中无用,并且可以通过编辑拼写错误轻松引入。

我欢迎警告,因为它可以轻松发现这种频繁的错误原因。

作为警告,你可以运行包含单例的代码,但最终将假设的任何值都将丢失。

我不认为 ISO 标准(从未听说过 ANSI )禁止此类变量。

你可以用这种方式重写你的例子

member(X, [Y|T]) :- X = Y ; member(X, T).

然后忘掉了单身人士。

答案 1 :(得分:10)

你有一个错误:

member(X,[X|T]) :- member(X,T).

实际上所说的(与你认为的相反)是member/2如果X位于列表的首尾并且< / strong>出现在列表的尾部。这个谓词只会在列表开头的同一件事的前N个副本中成立,所以这是一个非常奇怪的事情!

?- member(X, [a,a,c]).
X = a ;
X = a ;
false.

?- member(X, [b,a,a]).
X = b ;
false.

现在,您可以通过执行以下操作来纠正错误并仍然发出单身警告:

member(X, [Y|T]) :- member(X, T).

但这不如传统的两个头的定义或@ CapelliC的版本(+1)具有明确的OR。我认为你应该等到你更好地理解Prolog之后才能在Prolog代码美学方面投入大量资金。如果你坚持一段时间,你会发现这个警告以及匿名变量的使用。

单个变量在Prolog中无用的原因是它们被命名,但对它们一无所知,它们对其余的计算没有影响。下划线强调,在不影响含义的情况下,绝对可以进行任何事情。是什么让

member(X, [X|T]).

是的,X是位置1与位置2列表头部的X相同。列表必须为空或者有头部和尾部,但尾部的内容与此处无关,重要的是X也是头脑。 T可能是列表的其余部分,或者它可能是一个不正确的列表,或者它可能是一个面包箱或闪电或春天的空气气味。它与member(X, [X|T])的真相无关。

单身警告告诉你“你在这里预留了一个名字,但你从不用这个名字来称呼任何东西。”当我收到此消息时,我做的第一件事就是用_替换名称并查看我的代码是否仍然有意义。如果没有,我有一个逻辑错误。如果是这样,那可能就没必要了。

答案 2 :(得分:3)

您可以在SWI-Prolog FAQ

的官方页面上阅读相关内容

此警告出现的最常见情况是:

  1. 变量中的拼写错误
  2. 忘记使用/绑定变量
  3. SWI建议忽略它的一些方法:

    1. 为此目的使用名为_的匿名变量。
    2. 使用以_开头的变量(例如_T_X),以避免发出警告并记录您忽略的内容。
    3. 如果您知道自己在做什么,可以使用:- style_check(-singleton).并且所有警告都应该消失。