0
votes

I have a multiavailable predicate that returns true if an item is available at more than 1 location and false otherwise. It works correctly but when I pass in X it returns every possibility with duplicates. How would I get rid of these duplicates, because in one case true and false is given but in the other all the values are given. Here is my code and facts, the taqueria has a name, list of employees, and list of items:

taqueria(el_cuervo, [ana,juan,maria], 
        [carnitas_taco, combo_plate, al_pastor_taco, carne_asada_burrito]).

taqueria(la_posta, 
        [victor,maria,carla], [birria_taco, adobado_burrito, carnitas_sopa, combo_plate, adobado_plate]).

taqueria(robertos, [hector,carlos,miguel],
        [adobado_plate, guacamole_taco, al_pastor_burrito, carnitas_taco, carne_asada_burrito]).

taqueria(la_milpas_quatros, [jiminez, martin, antonio, miguel],  
        [lengua_sopa, adobado_plate, combo_plate]).
isin(X,[X|_]).
isin(X,[_|T]) :- isin(X,T).
available_at(X,Y) :- taqueria(Y,K,Z), isin(X,Z).
multi_available(X) :- available_at(X,Y),available_at(X,Z),not(Y==Z).
?- multi_available(carnitas_taco).
true

?- multi_available(lengua_sopa).
false

?- multi_available(X).

X = carnitas_taco ;

X = combo_plate ;

X = combo_plate ;

X = carne_asada_burrito ;

X = combo_plate ;

X = combo_plate ;

X = adobado_plate ;

X = adobado_plate ;

X = adobado_plate ;

X = adobado_plate ;

X = carnitas_taco ;

X = carne_asada_burrito ;

X = adobado_plate ;

X = adobado_plate ;

X = combo_plate ;

X = combo_plate ;

No
1
not(X==Z) can be written X \== Z. Also, your multi_available(X) actually succeeds (implicitly response with "true", just doesn't show it) for each successful X returned, then finally fails (shows "no", but implicitly responds "false") when it cannot find more solutions. Don't be too hung up about whether it displays true, false, or no.lurker
One way to get unique solutions is to use setof/3: setof(X, multi_available(X), Results). which yields a list Result of unique solutions. If you need them to pop out one at a time, then, setof(X, multi_available(X), Result), member(R, Result)..lurker
if i want setof to be in a function can I just do like function(X):-setof(X, multi_available(X), Result), member(R, Result). or do I need to call it function(X,Result)Anatoliy Sokolov
Of course. But it's a predicate, not a function.lurker

1 Answers

0
votes

I figured out another way I can do it by getting all the places each item is sold at and checking it the list of those for each item is at least 2 things.

helperm(X,L) :- bagof(A, available_at(X,A), L).
multi_available(X) :- helperm(X,[_,_|_]).