SWI prolog中?- 3=:=3.
true.
?- (3-2) =:= (9-8).
true.
?- 3 #= 3.
true.
?- (3-2) #= (9-8).
true.
和{{1}}之间有什么区别
我从SWI prolog中找到了这个定义,但仍然对此感到困惑
http://www.swi-prolog.org/pldoc/man?section=arithpreds
http://www.swi-prolog.org/pldoc/man?section=clpfd-arith-constraints
{{1}}
答案 0 :(得分:3)
SWI prolog中#=和=:=的区别是什么?
不同之处在于#=/2
是一个CLPFD库操作符(您需要执行:use_module(library(clpfd)).
才能使用它)并且它用于算术约束并包含is/2
和=:=/2
整数。这意味着你只能将它用于整数:
例如使用list会引发错误:
?- L #= [1,2,3].
ERROR: Domain error: `clpfd_expression' expected, found `[1,2,3]'
(同样使用=:=/2
中的列表会引发错误,列表示例仅用于理解两个运算符都用于表达式!)
对于整数,可以在任何可以使用=:=
的地方使用它,但如上所述,它可以用作is/2
,这意味着你可以使用它进行统一 - 只需将变量与某个整数绑定值,例如:
?- X #= 2.
X = 2.
上面没有检查X和数字2之间的相等性,因为X在无界变量中,它的作用是将X与值2绑定。
=:=/2
运算符无法实现这一点:
?- X =:= 2.
ERROR: Arguments are not sufficiently instantiated
ERROR: In:
ERROR: [8] _2494=:=2
ERROR: [7] <user>
那是因为=:=/2
仅用于检查是否相等!!
这是#=/2
和=:=/2
之间的差异。两个算术表达式之间的检查相等性,但使用=:=/2
时,应实例化所有变量。将#=/2
与变量一起使用时,这会在这些变量之间设置约束:
?- X #= 2.
X = 2. % constraints X to integer value 2
?- X + Y #= 2.
X+Y#=2. % constraints X,Y such that sum equals to 2 see next example:
?- X + Y #= 2 , X = 3.
X = 3,
Y = -1. % binds Y with -1 in order to succeed the constraint
?- X + Y #= 2 , X = 3 , Y > 0.
false. % false since constraint can't succeed!
正如您所看到的,#=/2
显然更具关系性,因为即使有一个约束多于一个变量,例如X + Y #= 2.
这也设置了X,Y之间的关系,绑定一个变量可以导致推理另一个。
在你的测试中你看到没有区别,因为你的所有变量都有值(例如它们被实例化),你只需检查两个运算符都能实现的相等性。
答案 1 :(得分:2)
见这个例子:
:- use_module(library(clpfd)).
solve_equation_1(X) :- X + 1 =:= 2.
solve_equation_2(X) :- X + 1 #= 2.
solve_equation_3(X,Y,Z) :- X + Y #= Z.
正如您所料,solve_equation_1
适用于实例化的X
,并且不适用于未实例化=:=
是一个检查表达式相等的简单运算符:
?- solve_equation_1(1).
true.
?- solve_equation_1(2).
false.
?- solve_equation_1(X).
=:=/2: Arguments are not sufficiently instantiated
#=
不是这种情况。它并没有真正检查任何东西 - 它只是声明某些变量和某些数字以某种特定的方式受到约束 - 例如他们形成一个等式。实际检查和计算将在以后进行,除非约束/等式非常简单,可以立即解决。这就是为什么非常简单的案例(例如您的示例)#=
可能看起来像=:=
。
请参阅这些示例 - =:=
都不可能,并且它们表明#=
的结果不是某些true / false布尔值,而是新约束:
?- solve_equation_2(X).
X = 1.
?- solve_equation_3(X,Y,2).
X+Y#=2.
?- X #= Y + Z, solve_equation_2(X).
X = 1,
Y+Z#=1