如何解决Prolog中的密码算术难题

cod*_*irl 5 prolog clpfd cryptarithmetic-puzzle

我必须编写一个Prolog程序来解决一个密码算术难题.

我需要编写一个函数solve([A,M,P,D,Y]),它将变量[A,M,P,D,Y]分配给0到9之间的值,使其满足方程AM + PM = DAY.每个变量都分配给一个不同的值,A,P和D不能等于0.

我开始编写这个函数,但在运行程序时遇到了问题.我将A,P和D的限制设置为不为零.当我通过算法时,我意识到D必须是1,所以我在程序的开头定义了它.我为M(M1和M2)定义了两个不同的变量,并将它们设置为彼此相等,因为拼图中的不同M应分配给相同的值.我为不同的变量分配了位置,并根据拼图添加了它们.我考虑了随附变量携带的任何变量.我的程序编译但函数不执行.

solve([A, M1, M2, P, D, Y]):- D is 1,
A/=0,
P/=0,
D/=0,
M1 = M2,
select(M1, [0,2,3,4,5,6,7,8,9], R1),
select(M2, R1, R2),
Y is (M1+M2) mod 10,
C1 is (M1+M2) // 10,
select(Y, R2, R3),
select(A, R3, R4),
select(P, R4, R5),
select(D, R5, R6),
A is (A+P+C1) mod 10,
D is (A+P+C1)// 10.
Run Code Online (Sandbox Code Playgroud)

我究竟做错了什么?我的变量定义有问题吗?我需要定义两个不同的M变量,还是一个足够?

ssB*_*Bee 3

这是我为您的难题提供的解决方案。我们只需依靠PROLOG的回溯即可。我们首先选择所有变量,然后检查拼图条件。我认为你不需要定义两个女士。

solve([A,M,P,D,Y]):- 
select(A,[0,1,2,3,4,5,6,7,8,9],WA), % W means Without
not(A=0),
select(M,WA,WMA),
select(P,WMA,WMAP),
not(P=0),
select(D,WMAP,WMAPD),
not(D=0),
select(Y,WMAPD,WMAPDY),
DAY is 100*D+10*A+Y,
AM  is 10*A+M,
PM  is 10*P+M,
DAY is AM+PM.
Run Code Online (Sandbox Code Playgroud)