%       filename:       nounvb
%       author:         pwg

% parse simple english sentence
% for time being just present as a list of identifiers
% also treats simple present tense with verb 'to be' + participle

% just deal with simple noun verb agreement
% i.e. have 'a dog bites a cat' & 'the dogs bite the cat'

:-use_module(library(lists)).

:-['ptree.pl'].

verb(v(V),sing) --> {verb(V)},[V].

verb(hates).
verb(loves).
verb(bites).

verb(v(Plural),plural) --> {verb(Sing),
                  sing_to_plrl_vb(Sing,Plural) },
                  [Plural].
% present participle with auxiliary

verb(v(A,P),SP) --> aux(A,SP),participle(P).

% present participles - would be better to generate from root!

participle(p(biting)) --> [biting].
participle(p(hating)) --> [hating].
participle(p(loving)) --> [loving].

% auxiliary verb - just 'is' and 'are' in our case

aux(a(is),sing) --> [is].
aux(a(are),plural) --> [are].
% singular verb ends in s chop off s


sing_to_plrl_vb(SVb,PVb) :-
        name(SVb,SLst),
        last_element(SLst,115), % s - 115 ascii
        remove_last(SLst,PLst),
        name(PVb,PLst).


% last element of a list

last_element([X],X):-!.

last_element([F|R],X):-
        last_element(R,X).

remove_last([X],[]) :-!.

remove_last([F|R],[F|R1]) :-
        remove_last(R,R1).

% singular and plural determiners

det(d(a),sing) --> [a].
det(d(every),sing) --> [every].
det(d(the),sing) --> [the].

det(d(the),plural) --> [the].
det(d(many),plural) --> [many].
det(d(all),plural) --> [all].
det(d(some),plural) --> [some].

noun(n(N),sing) --> {noun(N)},[N].

noun(man).
noun(girl).
noun(dog).
noun(fish).
noun(cat).

noun(n(people),plural) --> [people].

noun(n(PlNn),plural) --> { noun(Sing),
                   sing_to_plrl_noun(Sing,PlNn)},
                   [PlNn].

% simple noun phrase - determiner & noun

np(np(D,N),SP) --> det(D,SP),noun(N,SP).

% to cope with sentences like 'men love girls'

np(np(N),plural) --> noun(N,plural).

vp(vp(V,NP),SP) --> verb(V,SP),np(NP,_).

sentence(s(NP,VP)) --> np(NP,SP),vp(VP,SP).

sing_to_plrl_noun(fish,fish) :-!.
sing_to_plrl_noun(man,men) :-!.

% just add an 's'

sing_to_plrl_noun(Sing,Plrl) :-
        name(Sing,LSing),
        append(LSing,[115],PLst),
        name(Plrl,PLst).

% parse and display

parse_display(E) :-
    phrase(sentence(S),E),
    p_tree(S,0).
