Re: "maplist" for DCG?
"Richard A. O'Keefe" <[email protected]>
| Newsgroups | gmane.comp.ai.prolog.swi |
|---|---|
| Message-ID | <[email protected]> |
On 20/11/2013, at 6:21 AM, Alan Baljeu wrote:
> maplist(F, In, Out) is one thing, but how do you do the equivalent with a DCG, so the effect is something//2
> something(f, [In1, In2, In3])
> is equivalent to
> f(In1), f(In2), f(In3)
>
> where f/1 might be:
> f(X) --> { code(X,Y)}, [Y].
>
> In other words each input gets processed and appended to the DCG list. I feel like there's probably a standard predicate for this.
It's not quite clear to me what you want.
The analogue of the call/(N+1) family is
the phrase/(N+3) = phrase//(N+1) family,
where
% This is a ROUGH SKETCH of app/3.
% Efficiency and error checking have been
% thrown to the four winds.
app(M:T0, Zs, M:T1) :- !,
app(T0, Zs, T1).
app(T0, Zs, T1) :-
nonvar(T0),
T0 =.. [F|As],
append(As, Zs, AZ),
T1 =.. [F|AZ].
phrase(P, X1, S0, S) :-
app(P, [X1], P1),
phrase(P1, S0, S).
phrase(P, X1, X2, S0, S) :-
app(P, [X1,X2], P1),
phrase(P1, S0, S).
phrase(P, X1, X2, X3, S0, S) :-
app(P, [X1,X2,X3], P1),
phrase(P1, S0, S).
...
mapnt(NT, []) --> [].
mapnt(NT, [A|As]) --> phrase(NT, A), mapnt(NT, As).
In the absence of the phrase//(N+1) family,
mapnt(NT, []) --> [].
mapnt(NT, [A|As]) --> call(NT, A), mapnt(NT, As).
will probably do.
If you need the full power of phrase//(N+1),
and don't have an efficient implementation of it,
it would be better to do
mapnt(NT, As, S0, S) :-
mapnt_preprocess(As, NT, Gs),
phrase(Gs, S0, S).
mapnt_preprocess([], _, []).
mapnt_preprocess([A|As], NT, (G,Gs)) :-
app(NT, [A], G),
mapnt_preprocess(As, NT, Gs).
maplist(app(NT),