1

How can I verify if two lists represent the same relationship between their variables in any given order and then unify the corresponding variables?

For example the list:

[#=(_G13544,_G13547+1),#=(_G13553,_G13554),#=(_G13559,2),#>(_G13559, _G13544)]

would be equivalent to:

[#>(_G13453,_G13430),#=(_G13409,_G13355),#=(_G13453,2),#=(_G13430,1+_G13370)]

because both could be written as:

[A#>B,C#=D,A#=2,B#=E+1]

and the variable would be bound in the following way:

_G13453 = _G13559                  # Equivalent to A
_G13430 = _G13544                  # Equivalent to B
_G13409 = _G13553                  # Equivalent to C 
_G13355 = _G13554                  # Equivalent to D
_G13370 = _G13547                  # Equivalent to E

The functors are the following CLPFD operators:

  • Symmetrical: #=/2,+/2,-/2, and #\//2;
  • Not symmetrical: #>/2, and #</2;
  • Unary: abs/1
repeat
  • 18,496
  • 4
  • 54
  • 166
fpg1503
  • 7,492
  • 6
  • 29
  • 49
  • 1
    Is this homework? Or is there some context in which you need to do this? Asking because often _avoiding_ to do something complicated is easier than just doing it anyway. –  Oct 12 '15 at 06:33
  • I've made a program that uses CLPFD to solve some problems but I've noticed that most of them are really similar and I want it to solve similar inputs faster. – fpg1503 Oct 12 '15 at 16:15
  • I was hoping rather for some detail, as this usually makes it easier to find a solution... –  Oct 12 '15 at 17:41
  • I receive sets of constraints and I want to compare those with previous sets that were already solved. Every time my program solves a sets of constraints it rewrites itself to include a fact with the set of constraints and the result that was found. – fpg1503 Oct 12 '15 at 17:43

1 Answers1

0

something to get started

'same relationship between their variables'(L1, L2, Vs) :-
    copy_term(L1, T1),
    copy_term(L2, T2),
    numbervars(T1, 0, N),
    numbervars(T2, 0, N),
    rel_pairs(T1, T2, [], Vs).

rel_pairs([], [], B, B).
rel_pairs(Xs, Ys, B0, B2) :-
    select(X, Xs, Xr),
    select(Y, Ys, Yr),
    assign(X, Y, B0, B1),
    rel_pairs(Xr, Yr, B1, B2).

assign(A#=B, C#=D, B0, B2) :-
    assign(A, C, B0, B1),
    assign(B, D, B1, B2)
    ;
    assign(A, D, B0, B1),
    assign(B, C, B1, B2).
assign(A#>B, C#>D, B0, B2) :-
    assign(A, C, B0, B1),
    assign(B, D, B1, B2).

assign(A+B, C+D,  B0, B2) :-
    assign(A, C, B0, B1),
    assign(B, D, B1, B2)
    ;
    assign(A, D, B0, B1),
    assign(B, C, B1, B2).

assign('$VAR'(A), '$VAR'(B),  B0, B0) :-
    memberchk(A-B, B0), !.
assign('$VAR'(A), '$VAR'(B),  B0, [A-B|B0]) :-
    \+memberchk(A-_, B0),
    \+memberchk(_-B, B0), !.
assign(X, X, B, B).

surely there are a number of improvements that could be done...

CapelliC
  • 59,646
  • 5
  • 47
  • 90