26
clauses
Recognize(L) :- s(L), write("ФРАЗА РАСПОЗНАНА").
Recognize(_) :- write("*** ОШИБКА ! ФРАЗА НЕ РАСПОЗНАНА").
append([],L,L).
append([H|T],B,[H|C]) :- append(T,B,C).
S(L) :- append(L1,L2,L), L1=[1], S(L2).
S(L) :- append(L1,L2,L), L1=[1], B(L2).
S(L) :- append(L1,L2,L), L1=[0], A(L2).
A(L) :- append(L1,L2,L), L1=[0], A(L2).
A(L) :- append(L1,L2,L), L1=[0], B(L2).
B(L) :- append(L1,L2,L), L1=[1], S(L2).
B([]).
Более эффективным и простым будет следующий вариант программы, в
которой нет необходимости использовать процедуру деления списка на две
части:
/* АНАЛИЗАТОР РЕГУЛЯРНОЙ ГРАММАТИКИ – 2 . Вариант без предиката append */
goal
Recognize([1,1,1,1,1,0,0,0,0,0,0,1,1,0,0,0,0]).
clauses
Recognize(L) :- s(L), write("ФРАЗА РАСПОЗНАНА").
Recognize(_) :- write("*** ОШИБКА ! ФРАЗА НЕ РАСПОЗНАНА").
S([1|L]) :- S(L).
S([1|L]) :- B(L).
S([0|L]) :- A(L).
A([0|L]) :- A(L).
A([0|L]) :- B(L).
B([1|L]) :- S(L).
B([]).
Вернемся к вопросу о конечных состояниях. Смысл конечного
состояния заключается в определении условия завершения работы автомата.
Работа автомата может быть завершена при попадании его в одно из
заключительных состояний (такие состояния назовем поглощающими), и
тогда мы имеем дело с ПЛА. Однако условие завершения может быть более
сложным: работа автомата заканчивается тогда, когда входная
последовательность исчерпана и при этом автомат находится в одном из
терминальных состояний. Эта ситуация характерна для НЛА.
Реализовать недетерминированный автомат на Прологе достаточно
просто. А сделать то же самое на процедурном языке – задача весьма
нетривиальная. На практике поэтому предпочтительнее работать с
"нормальным", детерминированным автоматом, не допускающим
неоднозначностей.