В настоящей главе приводятся общие сведения о создании и использовании баз данных, кодовых таблиц и индексов. Дополнительные сведения о работе с этими объектами содержатся в следующих главах (в том числе в Главе 5, где описаны стандартные функции).
Под базой данных понимается файл с расширением ".dbf" (Формат его
соответствует формату файлов реляционных таблиц в стандарте xBase, но
поддерживает русские буквы в именах полей и длинные символьные поля).
Описание структуры базы данных выполняют в файле шаблона с расширением
".dbh" (обычно его имя совпадает с именем базы данных).
Пример файла шаблона (Doc.dbh)
FCOD C 1 - Код состояния документа NDOC N 6 - Исходный номер документа DDOC D - Исходная дата выписки документа DREG D - Дата регистрации поступления DATE D - Дата акцепта VD C 2 *vdtab - Вид документа ND N 6 - Номер документа NDE C 1 - Регистрационное расширение ND PD C 2 *rmtab1 - Рабочее место (подразделение) VDE C 2 *rmtab3 - Подвид док. BUH C 2 *buhtab - Бухгалтерия - автор BOX N 4 - Номер пачки SUMDOC N 18 2 - Сумма по документу VKD C 1 *vkstab - Картотека клиентов Дт NKD N 6 - Номер карточки Дт VKK C 1 *vkstab - Картотека клиентов Кт NKK N 6 - Номер карточки Кт OSNOV C 15 - Идентификатор основания OWNER N 4 - Инициатор документа SCRIPT C 400 - Описание документа RECDAT D - Дата последнего изменения USER C 4 0 6 0 - Подпись автора изменения RECNUM C 4 0 8 0 - Архивный номер POST C 2 - Почтовый номер
(Описание типов данных см. в п.1.4)
1.25, 2.5, 123456789, 123.456789 ...
1.25, 2.5, 123456789012345678, 123.456789012345678 ...
число десятичных знаков ----- NUM_ARRAY C 36 0 7 2 ---------- --- ----- --- --- имя поля тип длина всего после точки ------------------ размер элемента массива Обратите внимание: 36 - кратно 4, а не размеру элемента массива (т.е. 7).
SUM => NUM_ARRAY [Val (TAB_NO)] ;
LOG_ARRAY [@I+1] - просмотр суммы следующего месяца (если под системной переменной @I понимается расчетный месяц).
LETTER [@I], LETTER [@I + 1] ;
CHAR_ARRAY C 360 36 ---------- --- --- --- имя поля тип длина размер элемента массива поля В этом примере поле CHAR_ARRAY представлено в виде массива из 10 строк длиной по 36 байт каждая.
CHAR_ARRAY [@I], CHAR_ARRAY [@I + 1] ;
Пример. Кодовая таблица единиц измерения (EI.DIC) ------------------------------------------------- 166 166 1 Кг. 168 166 1000 Тонн 796 796 1 Шт. > ### 111 2222 **** (Символом '>' условно обозначен код '1A'). Строка шаблона содержит следующие поля: ### - Трехразрядное поле ключа. **** - Четырехразрядное поле комментария. 111 - Трехразрядное поле "главной" единицы измерения. 2222 - Четырехразрядное поле коэффициента перевода текущей единицы измерения в "главную".
При описании полей в строке шаблона повторяемые символы можно заменять точками, например поле (2222) можно описать как (2...), поле (****) как (*...) и т.д.
Пример. Кодовая таблица видов товарных картотек ------------------------------------------------ Клиенты Сотрудники Подразделения . #*............ В качестве ключа используется первая буква названия картотеки, а поле комментария примыкает непосредственно к ключевому полю.
Загрузка кодовой таблицы выполняется оператором CODETAB (или Codetab, codetab):
Примеры: -------- Codetab chtab ; /* chtab.dic - имя файла из каталога баз данных (в данном примере chtab.dic - план счетов) */ Codetab Count ( ".\count.mnu") ; /* count.mnu - файл в текущем каталоге */
PROF C 4 *proftab - Профессия здесь PROF - имя поля; С - его тип (символьный); 4 - его длина (4 байта); *proftab - имя файла с расширением ".dic", содержащего кодовую таблицу профессий.
PROF C 4 *proftab.dic - Профессия
Редактирование кодированных полей осуществляется по следующим правилам:
Открытие базы данных выполняется оператором USE (Use,use), имеющим следующий синтаксис:
Здесь :
Оператором HEADFILE cледует задавать имя_региона либо заключенное в круглые скобки имя_DBH_файла. Если задано и то и другое, то dbh - файл ищется по имени_DBH_файла, а региону присваивается имя_региона.
В дальнейшем к открытой базе данных можно обратиться только по ее внутреннему имени (псевдониму). Псевдоним назначается автоматически при трансляции оператора USE, исходя из следующих правил:
Отдельным оператором HEADFILE можно cоздать пустой регион с требуемой структурой для открытия реальных баз данных. При этом используется формат :
Текущей (активной) для задачи становится последняя из открытых оператором USE баз данных. Если в конкретном фрейме требуется изменить выбор текущей (активной) базы данных, следует использовать оператор SELECT (Select,select) в одном из форматов:
В примерах "BASEDIR" - каталог по умолчанию баз данных, который указывается в файле Z.CFG.
USE "tmp", HEADFILE = ("C:\subconto\client"); USE "tmp1", HEADFILE = ("C:\subconto\Client"); /* Первая база будет иметь псевдоним client, вторая - Client */ use "c:\z\base\dks" ; use "d:\swap\Dks" ; /* Первая база будет иметь внутреннее имя dks, вторая - Dks, хотя имя файла у них одинаково: DKS.DBF */ use "c:z\base\dks" ; use "d:\swap\dks", Headfile = ("c:\z\base\Dks") ; /* Обе базы данных имеют одинаковую структуру, которая задается одним и тем же файлом шаблона C:\Z\BASE\DKS.DBH */ use "dks" ; /* Открывается файл "DKS.DBF", из каталога BASEDIR */ use My_dir + "doc" ; /* Определяется имя файла как конкатенация двух строк, а затем открывается файл с соответствующим именем */ use ".\temp" ; /* Открывается или создается файл "TEMP.DBF" в текущем каталоге (а не в каталоге BASEDIR). Файл шаблона "TEMP.DBH" должен быть расположен в текущем каталоге */ use ".\temp", Headfile = tmp1 ; /* Открывается или создается файл "TEMP.DBF" в текущем каталоге. Файл "TMP1.DBH" должен быть расположен в каталоге BASEDIR */ use ".\temp", Headfile = c:\headers\tmp1 ; /* Открывается или создается файл "TEMP.DBF", в текущем каталоге пользователя. Файл шаблона "TMP1.DBH" должен быть расположен в каталоге "C:\HEADERS\" */
Для задания резидентного режима служит модификатор -r в одной из 2 форм:
use -r "client" ; /* Открытие базы "client.dbf" в расширенной памяти с полным кэшированием данного файла */ use -r:100 -c "fantom" ; /* Создание в оперативной памяти пустой базы данных по образу файла "fantom.dbf", либо "fantom.dbh" с размещением данных блоками по 100 записей */
Для задания этого режима служит модификатор -b:
block_factor - количество записей в блоке (блок-фактор),обязательный параметр буферизованного режима. Длина буфера определяется как произведение длины записи на блок-фактор и не должна превышать 64 килобайта. Буфер располагается в основной памяти.
Использование буферизованного режима иллюстрируется следующими примерами:
use -b:100 "dks" ; /* Открытие базы "dks.dbf" в буферизованном режиме для считывания */ use -i -b:100 "out" ; /* Открытие базы "out.dbf" в буферизованном режиме для записи (/считывания) */
Обратите внимание во втором примере на модификатор -i, удаляющий индексные файлы и делающий базу неиндексированной. Буферизация не дает эффекта для операций записи при наличии индексных файлов.
Для организации требуемого порядка и оперативности доступа к записям баз данных используются индексные файлы, формат которых совместим с файлами СУБД "CLIPPER" (расширение ".ntx") или "DBASE" (расширение ".ndx").
Опасная ошибка при работе с базами данных заключается в том, что прикладная программа модифицирует базу данных, не открыв всех необходимых индексных файлов. В этом случае неоткрытые индексные файлы теряют актуальность и становятся непригодными для последующего использования.
Во избежание этого система zCode использует списки индексных файлов. Такой список представляет собой файл, расположенный в том же каталоге, что и сама база данных ( dbf - файл). Он имеет имя, совпадающее с именем базы данных, а расширение - ".ils" (от "index list").
Во время выполнения оператора USE интерпретатор проверяет наличие списка индексных файлов и, если он имеется, открывает все индексные файлы по списку, независимо от фактической потребности в их наличии для той или иной программы. В случае их отсутствия они создаются заново.
Если по каким либо причинам индексное выражение, заданное в списке индексных файлов не совпадает с индексным выражением в заголовке соответствующего индексного файла, выдается диагностическое сообщение с запросом на реиндексирование.
Таким образом поддерживается целостность информационной системы при многопользовательской работе.
Описание индексных файлов в ils - файле строятся по следующему шаблону:
где:
Пример списка индексных файлов (M8001Z.ILS) ------------------------------------------- index = m8001z_1 ("FIO_B"); index = m8001z_2 ("STR(POS_B,6)+STR(TAB_B,8)"); index = m8001z_3 ("STR(TAB_B,8)"); index = m8001z_4 ("SUBSTR(STR(TAB_B,8),6,3)+FIO_B");
В программе за оператором USE или SELECT также могут следовать один или несколько операторов описаний индексных файлов. Они имеют следующий формат:
Если указано имя без пути, индексный файл располагаются в том же каталоге, что и база данных.
В программе индексное выражение задается только для временных индексных файлов. Временный индексный файл строится заново при каждом выполнении данной программы. Существующий индексный файл (из ils - файла) указывать нет необходимости (он открывается автоматически оператором USE), но во фрейме оператором SELECT следует выбрать активный индекс.
Пример описания индексных файлов: use "people" ; index -u = ind_1( "POSTNUM") ; index = ind_2( "DTOS( DATE) + FIO") ; Для базы people будут открыты все индексные файлы по списку из файла "people.ils", а файлы ind_1.ntx и ind_2.ntx будут строится заново при каждом исполнении программы.
people:p_date, people:ind_1, people:ind_2
Внутренние имена индексных файлов используются, например, в качестве параметра процедуры Seek() :
Seek( People:ind_1, "101025") ; /* Поиск в базе данных People записи, содержащей значение "101025" в поле POSTNUM */
При работе с индексированными базами данных часто используется также оператор KEY, предназначенный для выделения группы записей и имеющий следующий формат:
Для изменения активного индексного файла или отмены сортировки записей базы данных служит функция INDEX(), а для переустановки или отмены границ доступа к записям текущей базы данных - функция KEY().