Создание динамических баз данных
Достоинством Пролога является простота создания динамических баз данных. Основной задачей систем управления баз данных СУБД является добавление, удаление и корректирование записей в базе. Как известно из курса «Информационные системы», самая распространенная модель данных – реляционная.
Данные в реляционной базе данных представляются в виде таблицы. Под каждую запись в БД отводится одна строка, которая рассматривается как элемент отношения. Число элементов отношения является мощностью отношения. Число колонок (полей) в записи называется арностью. Имя колонки является атрибутом. Например, табличный список студентов:
ФИО Группа
№ студента
Фамилия, группа и номер образуют запись в базе, которую можно определить предикатом dstudent (name, groupe, position). Таким образом, можно установить следующие соответствия:
База данных Турбо Пролога |
Реляционная база |
Предикат базы |
Отношение |
Объект |
Атрибут |
Отдельное утверждение |
Элемент отношения |
Количество утверждений |
Мощность |
Имя предиката |
Имя таблицы |
Для работы с базами данных в Прологе имеются следующие встроенные предикаты.
- asserta – заносит новый факт в базу данных (БД) в ?????(ОЗУ). Заносит так, что новый факт помещается перед всеми ранее внесенными фактами.
- assertz – помещает новый факт в конец БД.
Например.
assertbase: - student (name, group, number),
assertz (dstudent (name, group, number)),
fail.
assertbase: -!.
- retract – удаляет утверждение из БД (удаляет конкретную запись)
Например, из записи убрать конкретного студента:
Retract (dstudent («Иванов», 461, 5))
Предикаты для работы с базой в целом:save – предикат, сохраняющий БД на диске из ОЗУ.
save (Dos_filename) – сохраняет из ОЗУ на диске.
- consult (Dos_filename) – считывает базу из файла на диске в ОЗУ. Consult неуспешен, если нет файла, неправильный синтаксис описания, нельзя разместить в ОЗУ из-за недостатка места.
- readterm (Domain, Term) – считывает из файла объекты, относящиеся к определенному домену: readterm(auto_record,auto(Name, Year, Price))
Пример:
domains
name = string
group = integer
number = integer
student(name, group, number)
readterm(dstudent, student(name, groupe, number))
Для получения списка всех студентов можно использовать предикат findall(Name, dstudent(Name, _, _), Namelist). Переменная Namelist будет содержать список всех имен.
При проектировании БД необходимо учитывать следующие факторы.
- Размер БД (для того, чтобы выбрать, где будет делаться база в ОЗУ или на диске).
- Организация элементов БД.
- Способы работы и содержание БД.
База данных создается в ОЗУ, если размер базы данных относительномал. Сначала необходимо задать начальные данные и создать базу. После того как БД создана, необходимо организовать её работу, которая включает следующее:
- занесение новых данных,
- удаление данных,
- выборка и вывод данных на экран.
Допустим, создаем базу данных студентов физического факультета, в которую заносим следующую информацию: фамилия, номер группы и номер студента в группе. Для работы с ней необходим предикат, кодирующий эту информацию.
student(p_name, /* полное имя (string) */
G_number,/* номер группы */
Pos ) /*номер в группе*/
Группа предикатов записывается в виде:
student(“Irina Fux, 484,5) и т.д.
Раздел domains
p_name=string
g_number,pos=integer
Предикаты динамической базы данных описываются в разделе Database:
dstudent (p_name, g_number, pos).
При запуске на выполнение, утверждения базы данных помещаются отдельно от обычных утверждений в оперативной памяти.
В разделе предикатов описываем все другие предикаты:
predicates
repeat
do_mbase
assert_database
menu
process(integer)
clear_database
student(p_name, g_number, pos)
error
Предикат student предназначен для задания начального содержимого базы данных. Эта информация засылается в утверждения предиката dstudent.
База данных «Студенты».
domains
p_name=string
g_number, pos=integer
database
dstudent(p_name, g_number, pos)
predicates
repeat
do_mbase
assert_database
menu
process(integer)
clear_database
student(p_name, g_number, pos)
error
goal
do_mbase
clauses
repeat
repeat:-repeat,
student(“Ivan Ivanov”, 543, 3)
student(.......)
assert_database:– student(P_name, G_name,Pos), assertz(dstudent(P_name, G_name, Pos), fail.
assert_databse:– !.
сlear_database:– retract(dstudent(_,_,_)), fail.
сlear_database:– !.
вo_mbase:– assert_database, makewindow(1, 7, 7, “Student Base”, 0, 0, 25, 80), menu, clear_database.
Menu:– repeat, clearwindow, write(«Text of help»), write(«Input choice(1,2,3,4):”), readint(Choice), nl, process(Choice), Choice=4, !.
Process(1):– makewindow(2, 7, 7, “Add student to base”, 2, 20, 18, 58), shiftwindow(2), write(“Input Name”), readln(P-name), write(“Input group”), readint(G-number), write(“Input number”), readint(Pos), assertz(dstudent(P_name, G_number, Pos)), write(P_name, “add to base”), nl, !, write(“press space”), readchar(_), removewindow.
Process(2):– makewindow(3, 7, 7, “Deleting”, 10, 30, 7, 40), shiftwindow(3), write(“Input Name”), readln(P_name), retract(dstudent(P_name,_,_)), write(P_name, “Deleted”), nl, !, write(“Press space”), readchar(_), removewindow.
Process(3):– makewindow(4, 7, 7, “review”, 7, 30, 16, 47), shiftwindow(4), write(“Input Name”), readln(P_name), dstudent(P_name, G_number, Pos), nl, write(“Name of student:”, P_name), write(“Group”, G_number), write(“Position”, Pos), nl, nl, !, write(“Space”), readchar(_), removewindow).
Process(3):– makewindow(5, 7, 7, ”Nobody”, 14, 7, 5, 60), shiftwindow(3), write(“Cant find”), nl, nl, write(“Sorry”), nl, !, write(“Space”), readchar(_), removewindow, shiftwindow(1).
Process(4):– write(“Are you shure?/Y/N”), readln(Answer), frontchar(Answer, ’Y’,_), !.
Process(Choice):– Choice<1, error.
Process(Choice):– Choice>4, error.
Error:– write(“Input number from 1 to 4”), write (“Space”), readchar(_).
Базы данных можно хранить и на внешних носителях. В этом случае к вышеприведенной программе добавляются правила чтения и записи внешних файлов. Вспомогательные модули dbassert и dbass заносят в базу новые данные. Вводятся два терма, обозначающие файл базы данных и служебный индексный файл.
domains
file=datafile; indexfile
name=string
group=integer
database
team(name, group)
predicates
repeat
menu
process(integer)
do_base
dbassert(dbasedom) – содержит ссылки на файл базы данных и служебный файл
dbass(dbaedom, string, string)
dbretract(dbasedom)
dbret(dbasedom, string, string) – ищет запись и удаляет
dbret1(dbasedom, real)
dbread(dbasedom)
dbrd(dbasedom, string, string) – ищет и читает данные
dbaaccess(dbasedom, real) –ищет и читает в индексном файле
goal
do_dbase
clauses
co_dbase:– makewindow(1, 7, 7, “Kurse”, 0, 0, 24, 80), menu.
menu:–repeat, clearwindow, nl, write(“1.add 2delete 3 review 4 exit”), nl, write(“Input choice 1 2 3 4”), readint(Choice), nl, Choice>0, Choice<5, process(Choice), Choice=4, !.
Process(1): – аналогично предыдущей программе/