How to write in a standard conforming manner avs_term_rearranged(AVs, T, AVsR) with given AVs and T such that AVsR is a p
My previous answer had quadratic runtime complexity. If that's a problem, here is a linear alternative. The reason this is a bit tricky is that unbound variables cannot be used as keys for hashing etc.
As before, we basically rearrange the list AVs such that its elements have the same order as the variables in the list Xs (obtained from term_variables/2). The new idea here is to first compute a (ground) description of the required permutation (APs), and then construct the permutation of AV using this description.
avs_term_rearranged(AVs, T, AVRs) :-
term_variables(T, Xs),
copy_term(AVs-Xs, APs-Ps),
ints(Ps, 0, N),
functor(Array, a, N),
distribute(AVs, APs, Array),
gather(1, N, Array, AVRs).
ints([], N, N).
ints([I|Is], I0, N) :- I is I0+1, ints(Is, I, N).
distribute([], [], _).
distribute([AV|AVs], [_=P|APs], Array) :-
nonvar(P),
arg(P, Array, AV),
distribute(AVs, APs, Array).
gather(I, N, Array, AVRs) :-
( I > N ->
AVRs = []
;
arg(I, Array, AV),
I1 is I+1,
( var(AV) -> AVRs=AVRs1 ; AVRs = [AV|AVRs1] ),
gather(I1, N, Array, AVRs1)
).