Is it possible to solve the following problem in Prolog
?
Let A
and B
be lists of numbers and let N
be a number. It is known that B
is sorted decreasingly. Check if N
can be inserted into A
so that the result is B
, but do not bind any variable that occurs as a tail in either A
nor B
.
For example
?- insertable(34, [78, 72, 11 | Z], [78, 72, 34, 11 | Z]).
true.
?- insertable(34, [78, 72, 11 | Z], L).
L = [78, 72, 34, 11 | Z].
Can anyone help me? :)
EDIT 1: This is what I came up with.
insertable(X, List1, List2):- select(X, List2, List1), sorted(List2).
sorted([]).
sorted([_]).
sorted([X, Y | Rest]) :-
X > Y,
sorted([Y | Rest]).
However, even though it works as expected when the arguments are fully instantiated, it binds variables located in tails:
?- insertable(11, [5, 3, 2], [11, 5, 3, 2]).
true .
?- insertable(11, [5, 3, 2 | X], [11, 5, 3, 2 | X] ).
X = [] .
?- insertable(11, [5, 3, 2 | X], L ).
X = [],
L = [11, 5, 3, 2] .
EDIT 2: Here's another approach that I tried.
in(X, [], [X]).
in(X, [Head | Tail1], [Head | Tail2]) :-
X =< Head,
in(X, Tail1, Tail2).
in(X, [Head | Tail], [X, Head | Tail]) :-
X > Head.
The problem is still there:
?- in(1, [3, 2], [3, 2, 1]).
true ;
false.
?- in(1, [3, 2], L).
L = [3, 2, 1] ;
false.
?- in(1, [3, 2 | X], L).
X = [],
L = [3, 2, 1] ;
ERROR: =</2: Arguments are not sufficiently instantiated
Exception: (9) in(1, _G8394089, _G8394190) ? abort
% Execution Aborted
?- in(1, [3, 2 | X], [3, 2, 1 | X]).
X = [] ;
X = [1] ;
X = [1, 1] ;
X = [1, 1, 1] ;
X = [1, 1, 1, 1] ;
X = [1, 1, 1, 1, 1] ;
X = [1, 1, 1, 1, 1, 1] ;
X = [1, 1, 1, 1, 1, 1, 1] .