what's the difference between #= and =:= in SWI prolog

馋奶兔 提交于 2019-12-22 10:44:23

问题


What is the difference between #= and =:= in SWI prolog.
I have found the definition from SWI prolog, but still confused about it.
http://www.swi-prolog.org/pldoc/man?section=arithpreds

http://www.swi-prolog.org/pldoc/man?section=clpfd-arith-constraints

?- 3=:=3.
true.

?- (3-2) =:= (9-8).
true.

?- 3 #= 3.
true.

?- (3-2) #= (9-8).
true.

回答1:


What's the difference between #= and =:= in SWI prolog ?

The difference is that #=/2is a CLPFD library operator (you need to execute: use_module(library(clpfd)). in order to use it ) and it is used for arithmetic constraints and subsumes both is/2 and =:=/2 over integers. What this means is that you can use it only for integers:

e.g using list will raise error:

?- L #= [1,2,3].
ERROR: Domain error: `clpfd_expression' expected, found `[1,2,3]' 

(Also using lists in =:=/2 will raise error ,the list example is just for understanding that both operators are used for expressions !)

For integers it can be used anywhere =:= could be used but as mentioned above it can be used as is/2 which means that you can use it for unification - simply to bind a variable with some integer value, for example:

?- X #= 2.
X = 2.

the above does not check for equality between X and number 2 since X in unbounded variable, what it does is bonding X with value 2.

This is not possible with =:=/2 operator:

?- X =:= 2.
ERROR: Arguments are not sufficiently instantiated
ERROR: In:
ERROR:    [8] _2494=:=2
ERROR:    [7] <user>

That's because =:=/2 is used only to check for equality !!

This is the difference between #=/2 and =:=/2. Both check for equality between two arithmetic expressions but when using =:=/2 all variables should be instantiated. When using #=/2 with variables this sets constraints between these variables:

?- 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!

As you can see #=/2 is clearly more relational since even when having a constraint with more that one variable e.g X + Y #= 2. this sets a relation between X,Y, binding one variable can lead to reasoning on the other.

In your tests you see no difference since all your variables have values (e.g they are instantiated) and you simple check for equality which both operators an achieve.




回答2:


See this examples:

:- 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.

As you might expect, solve_equation_1 works for instantiated X and doesn't for uninstantiated as =:= is a simple operator checking equality of expressions:

?- solve_equation_1(1).
true.

?- solve_equation_1(2).
false.

?- solve_equation_1(X).
=:=/2: Arguments are not sufficiently instantiated

This is not the case for #=. It does not really check anything - it just states that some variables and some numbers are constrained in some specific way - e.g. they form an equation. Real checks and calculations take places later unless the constraint/equation is so simple that it can be solved immediately. That's why for very simple cases (like your examples) #= might look like =:=.

See these examples - all are impossible for =:= and they show that result of #= is not some true/false boolean value but new constraints:

?- 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


来源:https://stackoverflow.com/questions/46756842/whats-the-difference-between-and-in-swi-prolog

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!