Open yossigil opened 2 years ago
Hi,
I am suggesting the following code for solving the issue:
For identifying the correct syntax of Prolog programs, I am suggesting the following code, based on
/* Structure Analysis: */
prolog([]). % empty string a a valid program
prolog([rule(_,_)|Rs]) :- prolog(Rs).
prolog([query(_)|Rs]) :- prolog(Rs).
query(Xs) :- terms(Xs).
rule(X,[]) :- atom_prolog(X). % rule has to have a L-side, but not necessarily a R-side (fact)
rule(X,Xs) :- compound_prolog(X), terms(Xs).
compound_prolog([X|Xs]) :- functor(X), terms(Xs). % nullary relations are not allowed
terms([X]) :- term(X).
terms([X|Xs]) :- term(X), terms(Xs).
term([X]) :- rule(X,[]). % is it correct?
term([X|Xs]) :- rule(X,Xs).
atom_prolog(X) :- constant(X).
atom_prolog(X) :- variable(X).
/* String Analysis: */
constant(S) :- atom_concat(X,Xs,S),
check_in(X,['a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z']),
check_all_in(Xs,['A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z','0','1','2','3','4','5','6','7','8','9']).
variable(S) :- atom_concat(X,Xs,S),
check_in(X,['A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z']),
check_all_in(Xs,['A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z','0','1','2','3','4','5','6','7','8','9']).
variable(S) :- atom_concat('_',Xs,S),
check_all_in(Xs,['A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z','0','1','2','3','4','5','6','7','8','9']).
functor(S) :- atom_concat(X,Xs,S),
check_in(X,['a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z']), % should we allow capitalization?
check_all_in(Xs,['A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z','0','1','2','3','4','5','6','7','8','9','<','>','!','@','#','$','%','^','&','*','-','\\','=','+','\'','"','/']).
/* Auxiliary String Analysis: */
check_all_in("",_).
check_all_in(S,L) :- atom_concat(X,Xs,S), check_in(X,L), check_all_in(Xs,L).
check_in(X,[X|_]). % it should work even when X is the last character in the list
check_in(X,[_|Ls]) :- check_in(X,Ls).
The code is also available at the following link. The structural analysis in the code is based on the BNF presented in the discussion of #1 . It is probably not the simplest way to solve the issue, but it is similar to the inheritance hierarchy that already exists in the project.
I have tested the code on some examples, for instance:
?- prolog([]).
, which is true
.equals(X,Y).
is equivalent to ?- prolog([rule(compound_prolog("equals",["X", "Y"]), [])]).
, which is true
.?-
is equivalent to ?- prolog([query()]).
, which is false
(empty query is not allowed).?- prolog(X).
, which prints (first three results): []
(empty program), [rule(_1418, _1420)]
(a program with a single rule, with two internal variables), [rule(_1464, _1466), rule(_1476, _1478)]
(a program with two rule, each with two internal variables).I am not sure that the code treats nullary relations correctly, it might be worth checking.
If this code satisfies the constraints, the issue can be closed.
Write Prolog terms and functors to express the Prolog syntax, e.g., term(Atom, list of Terms). rule(Right, Left).
And then write a program that goes over the term and produces random Prolog programs.