views:

132

answers:

3

What's an elegant way to unify X,Y with (1,2), (1,-2), (-1,2), (-1,-2), (2,1), (2,-1) , (-2,1), (-2,-1)?

Doing it this way seems error prone and tedious:

foo(1,2).
foo(1,-2).
foo(-1,-2).
...
...
...

And this way seems too expensive:

foo(X,Y) :-
  L = [1,-1,2,-2],
  member(X,L),
  member(Y,L),
  abs(X,X1), abs(Y,Y1),
  X1 =\= Y1.
+1  A: 

A further development on what was commented:

generate_pairs_foo(X,Y) :-
  L = [1,-1,2,-2],
  member(X,L),
  member(Y,L),
  abs(X,X1), abs(Y,Y1),
  X1 =\= Y1.

assert_all_foo([]).

assert_all_foo([(X,Y)|T]) :-
  assert(foo(X,Y)), assert_all_foo(T).

find_all((X,Y),generate_pairs_foo(X,Y),L), assert_all_foo(L).

Hmmmmmm... look, it's easier and shorter to just write all the cases xD

fortran
I really think the other's answers are clearer... maybe you should accept one of them (unless you're looking for a solution to bigger and more general cases that cannot be handled that way).
fortran
+3  A: 
foo0(X,Y):-
    member(X,[1,-1]),
    member(Y,[2,-2]).

foo(X,Y):-
    foo0(X,Y);
    foo0(Y,X).
Xonix
I'll upvote if you put the ; on a line of its own.
starblue
+2  A: 
foo(1, 2).
foo(2, 1).
foo(X, Y) :-
   foo(-X, Y).
foo(X, Y) :-
   foo(X, -Y).
Daren Thomas