Re: How to replace a term to the inside of an other term?



Joachim Schimpf wrote:
student wrote:

If you wish to restrict the replacement of occurrences a functor that
may occur with different arities in the same term to occurrences that
have some particular arity then you must specify which one it is.

And why stop here? You may want to replace certain patterns
by other patterns,

I could not agree more.
(Please see my reply to Bart).

e.g.

?- replace(3*3 + 4*4, X*X, twice(X), Out).
X = X
Out = twice(3) + twice(4)
Yes (0.00s cpu)


?- replace(foo(1,foo(2,3)), foo(X,Y), bar(Y,X), Out).
X = X
Y = Y
Out = bar(bar(3, 2), 1)
Yes (0.00s cpu)


?- replace(foo(bar(baz)), foo(bar(X)), foobar(X), Out).
X = X
Out = foobar(baz)
Yes (0.00s cpu)



replace(In, OldTmpl, NewTmpl, Out) :-
functor(In, F, N),
functor(In1, F, N),
replace_args(N, In, OldTmpl, NewTmpl, In1),
( copy_term(OldTmpl-NewTmpl, Old-New), In1 = Old ->
Out = New
;
Out = In1
).

replace_args(I, In, OldTmpl, NewTmpl, Out) :-
( I > 0 ->
arg(I, In, InArg),
arg(I, Out, OutArg),
replace(InArg, OldTmpl, NewTmpl, OutArg),
I1 is I-1,
replace_args(I1, In, OldTmpl, NewTmpl, Out)
;
true
).


-- Joachim

Beautiful stuff, especially the concept of patterns with variables
that somehow end up not being instantiated, but I will have to find time
to bone up on 'functor/3', 'copy_term/3', and 'arg/3' to understand it.

Cheers.
--
billh
.



Relevant Pages