home *** CD-ROM | disk | FTP | other *** search
- /************************************************************************
- * *
- * The SB-Prolog System *
- * Copyright SUNY at Stony Brook, 1986; University of Arizona, 1987 *
- * *
- ************************************************************************/
-
- /*-----------------------------------------------------------------
- SB-Prolog is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY. No author or distributor
- accepts responsibility to anyone for the consequences of using it
- or for whether it serves any particular purpose or works at all,
- unless he says so in writing. Refer to the SB-Prolog General Public
- License for full details.
-
- Everyone is granted permission to copy, modify and redistribute
- SB-Prolog, but only under the conditions described in the
- SB-Prolog General Public License. A copy of this license is
- supposed to have been given to you along with SB-Prolog so you
- can know your rights and responsibilities. It should be in a
- file named COPYING. Among other things, the copyright notice
- and this notice must be preserved on all copies.
- ------------------------------------------------------------------ */
- /* $dcg.P */
-
-
- % File: $dcg.P
- % Author: Saumya K. Debray
- % Date: March 15, 1988
- %
- % This is a straightforward translator for DCGs.
- %
- % Bugs: pushback lists in the heads of rules are not handled. This
- % is a rarely used feature, and I didn't see it worth my while to
- % complicate life for this.
-
- $dcg_export([$dcg/2,$phrase/2,$phrase/3]).
-
- $dcg_use($meta,[functor/3,_,_]).
- $dcg_use($bio, [$writename/1,_,_,$nl/0,_,_,_,_,_,_,_,_,_,_,_]).
-
-
- $dcg(Rule, (OutHd :- OutBody)) :-
- nonvar(Rule),
- Rule = (Lhs --> Rhs),
- (functor(Lhs,',',2) ->
- ($writename('*** Pushback lists in DCG Rule heads not implemented!'),
- $nl,
- fail
- ) ;
- $add_io_args(Lhs, In, Out, OutHd)
- ),
- $dcg_body(Rhs, In, Out, OutBody).
-
- $add_io_args(Term, In, Out, NewTerm) :-
- functor(Term,P,Arity),
- NewArity is Arity + 2,
- N1 is Arity + 1,
- functor(NewTerm,P,NewArity),
- arg(N1,NewTerm,In),
- arg(NewArity,NewTerm,Out),
- $dcg_fillin_args(Arity,Term,NewTerm).
-
- $dcg_fillin_args(N,T1,T2) :-
- N =:= 0 ->
- true ;
- (arg(N,T1,Arg), arg(N,T2,Arg),
- N1 is N - 1,
- $dcg_fillin_args(N1,T1,T2)
- ).
-
- $dcg_body(Rhs,In,Out,Goal) :-
- var(Rhs) ->
- $dcg_body_var(Rhs,In,Out,Goal) ;
- $dcg_body_nonvar(Rhs,In,Out,Goal).
-
- $dcg_body_var(Rhs,In,Out,Goal) :-
- In = Out,
- Goal = ($writename('*** Error: variable in RHS of DCG Rule!'),
- $nl,fail),
- $writename('*** Error: variable in RHS of DCG Rule!'),
- $nl.
-
- $dcg_body_nonvar(','(G1,G2),In,Out,','(T1,T2)) :-
- !,
- $dcg_body(G1,In,Mid,T1),
- $dcg_body(G2,Mid,Out,T2).
- $dcg_body_nonvar(';'(G1,G2),In,Out,';'(T1,T2)) :-
- !,
- $dcg_body(G1,In,Out,T1),
- $dcg_body(G2,In,Out,T2).
- $dcg_body_nonvar('->'(G1,G2),In,Out,'->'(T1,T2)) :-
- !,
- $dcg_body(G1,In,Mid,T1),
- $dcg_body(G2,Mid,Out,T2).
- $dcg_body_nonvar(not(G),In,Out,not(T)) :-
- !,
- $writename('*** Warning: not/1 in DCG rule may not be sound!'),
- $nl,
- $dcg_body(G,In,Out,T).
- $dcg_body_nonvar('\+'(G),In,Out,not(T)) :-
- !,
- $writename('*** Warning: \+ in DCG rule may not be sound!'),
- $nl,
- $dcg_body(G,In,Out,T).
- $dcg_body_nonvar('{}'(G),In,Out,(In = Out, call(G))) :- !.
- $dcg_body_nonvar('!',In,Out ,(In = Out, '!')) :- !.
- $dcg_body_nonvar([],In,Out,(In = Out)) :- !.
- $dcg_body_nonvar(L,In,Out,G) :-
- (L = [_|_], $dcg_list(L)) ->
- $dcg_terminal(L,In,Out,G) ;
- $add_io_args(L,In,Out,G). /* nonterminal */
-
- $dcg_list([]).
- $dcg_list(L) :-
- nonvar(L) ->
- (L = [_|L1], $dcg_list(L1)) ;
- ($writename('*** Error: variable within a list of terminals in DCG rule'),
- $nl,
- fail
- ).
-
- $dcg_terminal([],In,Out,(In = Out)).
- $dcg_terminal([H|L],In,Out,','('C'(In,H,Mid),G)) :-
- $dcg_terminal(L,Mid,Out,G).
-
- 'C'([X|S],X,S).
-
- $phrase(P,L) :-
- nonvar(P) ->
- $phrase(P,L,[]) ;
- ($writename('*** First argument to phrase/2 must be nonvariable!'),
- $nl,
- fail
- ).
-
- $phrase(P,In,Out) :-
- $dcg_body_nonvar(P,In,Out,Goal),
- call(Goal).
-
- /* ------------------------- end $dcg.P ------------------------- */
-
-