Пример реализации экспертной системы на языке Пролог

В завершение раздела приведем полный листинг программы на языке Пролог, которая выводит все цепочки взаимозачетов предприятий, имеющихся в базе знаний, и производит зачет по выбранной цепочке.

/* Экспертная система "Взаимозачет" */ domains

list_str = string* list_list = list_str* database — cep

cep (list_str, integer) database — db

db_dan (string, integer, string) predicates

dolg (string, integer, list_str)

prinad (string, list_str)

min (integer, integer, integer)

vivod (list_str)

run

wr (list_list, integer) analis

el_num_in_list (integer, list_list, list_str) zachet (list_str, integer)

goal

run. clauses run: -

makewindow (1, 23, 23, 0, 0, 25, 80),

makewindow (2, 33, 44, "Взаимозачеты ", 3, 5, 20, 70) ,

write ("Составить цепочки взаимозачетов"), nl, write ("Введите первого должника: ") ,

/* правило, управляющее работой программы */ readln (X),

write ("Введите сумму: "), readint (Sum), nl,

write ("Цепочки должников: "), nl, consult ("db. txt", db), not (dolg (X, Sum, [X] ) ) , nl, analis, nl,

retractall (cep ( _, _)),

write ("Для завершения работы нажмите любую

клавишу.") ,

readchar ( _) ,

removewindow,

removewindow.

/* Правило осуществляет поиск цепочки должников */ dolg (X, Sum, Z):-

db_dan (X, Suml, Y), min (Sum, Suml, Sum2) , not (prinad (Y, Z)), dolg (Y, Sum2, [Y | Z]). dolg (X, Sum, L)

not (db_dan (X, _, _) ) , not (L= [X]), not (cep (L, _) ), asserta (cep (L, Sum)), fail.

/* правило определяет принадлежность элемента списку */ prinad (X, [X | _])!. prinad (X, [ _ | Y]):- prinad (X, Y).

/* правило определяет минимальный из двух элементов */ min (S, SI, S) : - S < S1, ! . min ( _, SI, SI) .

/* правило осуществляет вывод элементов */

/* списка (одной цепочки должников) */ vivod ( []) :- ! . vivod ( [Н | List]):- write (Н), nl, vivod (List).

/* правило выводит все цепочки */ wr ( [],_):- !. wr ( [Н | L], N) :-

write ("Цепочка номер ", N, ":"), nl,

vivod (H), cep (H, S), write ("Сумма зачета: ",

S), nl,

readchar ( _), nl, N1=N+1, wr (L, N1) .

/* правило производит зачет по заданному номеру цепочки */

analis:-

findall (L, сер (L, _), List), not (List = []), wr (List, 1),

write ("Введите номер цепочки: "), readint (N),

el_num_in_list (N, List, NL), cep (NL, S),

write ("Сумма зачета: ", S), nl, zachet (NL, S), write ("Зачет произведен."), save ("db. txt", db),!. analis :- write ("Должников нет!").

/* правило находит в списке элемент по заданному номеру */

el_num_in_list (1, [Н | _], Н):-!. el_num_in_list (N, [ _ | List), NL):-

N1=N-1,

el_num_in_list (N1, List, NL).

/* правило производит изменения в базе данных (зачет) */

3.9. Диалекты и языки, используемые для задач искусственного интеллекта » 75

zachet ( [ _], _)!. zachet ( [Н | [HI | NL]], S) zachet ( [HI | NL], S), db_dan (HI, SI, H),

S2=S1-S,

retract (db_dan (HI, SI, H)), asserta (db_dan (HI, S2, H)).

/* конец листинга программы */

 
Посмотреть оригинал
< Пред   СОДЕРЖАНИЕ   ОРИГИНАЛ   След >