
- •"Грамматика"
- •1. Общая характеристика системы
- •3. Анализ текста на формальном языке
- •4. Пользовательский интерфейс системы
- •5. Порядок выполнения лабораторных работ
- •6. Задания к лабораторному практикуму
- •Пример грамматики с вызовами семантических процедур
- •Интерфейс программ семантического анализа с планом семантических действий
Пример грамматики с вызовами семантических процедур
Программа ::=
program <_Name_> (_0_);
[_ <_ Константы _> _] [_ <_ Переменные _> _] begin
{_ <_ Операция _> _} end. (_10_)**
Константы = const {_ <_Name_> (_1_) = <_Число_> (_2_); _} **
Число = ?_ <_Numb_> _|_ <_Real_> _? **
Переменные = var {_ <_Name_>(_3_) {_ ,<_Name_>(_4_)_} : <_Стандартный_тип_> ;_} **.. Стандартный_тип ::=?_ word _|_ byte _|_ char _|_ real _?(_5_) ** Операция ::= <_Name_> (_6_) := <_ Выражение_> (_ 9 _)**
Выражение ::= <_Операнд_> {_ <_Знак_Операции _> <_Операнд_> _} ; **
Операнд ::= ?_ <_Name_> _|_ <_Numb_> _|_ <_Real_> _? (_7_) **
Знак_Операции ::=?_ + _|_-_|_ *_|_/_|(_8_) **
ПРИЛОЖЕНИЕ 2
Интерфейс программ семантического анализа с планом семантических действий
Для создания Turbo Pascal-программы, осуществляющей семантический анализ предложений на ФЯ, необходимо иметь в наличии и указать компилятору Turbo Pascal 7 модулей: GBase1.tpu, GBase2.tpu, GBase3.tpu, tpcrt.tpu, tpinline.tpu, tpmemchk.tpu, tpstring.tpu. Последние 4 из них принадлежат пакету Turbo Professional фирмы TurboPower, с использованием которого написан ряд функций системы "Грамматика". Модуль, осуществляющий семантический анализ, должен импортировать Gbase3, который содержит:
класс SemPointer, обеспечивающий работу с планом семантических действий,
тип SemWordT, определяющий структуру одной строки плана (записи файла).
Класс SemPointer SemUserT = object (...)
constructor Init;
function SFOpen( file_name: string): boolean;
function GetWord( var sr: word; var sw: SemWordT): boolean;
procedure SFWrite( sw: SemWordT );
function SFReset( t: word ): boolean;
destructor Done;
end;
SemPointer=^SemUserT;
constructor Init;
Вызов конструктора Init необходим для корректной работы прочих процедур.
function SFOpen( file_name: string): boolean;
Функция SFOpen имеет единственный параметр - имя файла, содержащего план семантических действий в двоичной форме. Функция возвращает значение True, если файл найден и инициированы все необходимые данные. Значение False свидельствует о невозможности выполнения дальнейших действий с данным планом.
function GetWord( var sr: word; var sw: SemWordT): boolean;
Функция GetWord предназначена для получения следующей записи плана. Функция возвращает значение True в случае корректного получения очередной записи. False - в противном случае. Через параметр sr передается код ошибки:
0: ошибок нет;
1: файл семантических данных не открыт;
2: ошибки при получении семантического слова;
3: чтение файла после исчерпания данных;
4: повторное сообщение об ошибке.
Procedure SFWrite( sw: SemWordT);
Процедура выводит на экран дисплея значение полей параметра sw.
Procedure SFReset( t: word ): boolean;
Процедура, в зависимости от значения параметра t, удаляет файл с планом (t=1) или закрывает его (t=2). Обращение к ней обязательно после завершения семантического анализа.
Destructor Done;
Процедура завершает цикл работ с планом и связанной с ним динамической переменной типа SemUserT.
Тип SemWordT Туре
SWType = ( Snoth, Seof, Ssw, Sss, Sname, Snumb, Sreal); SemWordT = Record
sa : Word; { номер семантической процедуры }
swp: TextPosition; { позиция слова в анализируемом предложении }
Case swt: SWType of
Snoth: ( ); { ничего }
Seof: ( ); { конец файла }
Ssw : ( swsw: string ); { ключевое слово языка)
Sss : ( swss: string); { разделитель языка}
Sname: ( swn : string ); { идентификатор }
Snumb: ( sww: word ); { число целое без знака }
Sreal: ( swr: real ) { число вещественное без знака }
end;
TextPosition = Record { позиция точки в тексте )
lp: word1; { файловая позиция начала строки }
sh: word; { смешение по строке к точке, т.е. файловая позиция точки есть (lp+sh)}
ln: word { номер данной строки, считая с 0 }
end;
ПРИЛОЖЕНИЕ 3
ПРИМЕР ПРОГРАММНОЙ РЕАЛИЗАЦИИ СЕМАНТИЧЕСКОГО АНАЛИЗАТОРА
program Sem_Example;
{
Данная программа осуществляет семантический анализ текста на ФЯ.
Исходными данными для анализа является план семантических действий (ПСД) в двоичной форме, формируемый системой Грамматика для корректных в синтаксическом отношении текстов.
Результат семантического анализа - файл с перечнем номеров и параметров семантических процедур, содержащихся в ПСД.
Имена и расширения имен исходного и порождаемого файлов задаются константами. }
uses Dos, TPCrt, GBase3;
const
SemFileName = 'sem_exam'; { имя файла, содержащего описание на ФЯ}
SernFileExt = 'smb'; { расширение имени файла, содержащего план }
{семантических действий}
ResFileExt = 'res'; { расширение имени формируемого файла }
var
Sem: SemPlanPointer; { переменная - план семантических действий }
sw: SemWordT; { очередная одна строка ПСД (запись файла)}
gr: word; { код результата чтения очередной строки ПСД }
tf: text; { файл, в который записывается результат семантического, анализа }
i: word; { рабочая переменная, используемая при создании файла }
procedure SemAction( sw: SemWordT); { процедура интерпретации строки ПСД}
{ интерпретация состоит в записи в файл, определяемый глобальной переменной tf, номера и параметра семантического действия }
begin
WriteLn( tf); WriteLn( tf,' Сем. действие:', sw.sa ); with sw do begin
WriteLn( tf,' Позиция в тексте (строка,столбец):', swp.ln+1,',', swp.sh+1 ); case swt of
Snoth : WriteLn( tf,' Параметр отсутствует'); Ssw : WriteLn( tf,' Ключевое слово:', swsw ); Sss : WriteLn( tf,' Разделитель:', swss); Sname : WriteLn( tf,' Имя :', swn); Snumb : WriteLn( tf,' Целое число:', sww); Sreal : WriteLn( tf,' Вещественное число :', swr); Seof : WriteLn( tf,' Конец файла');
else WriteLn( tf, 'не обрабатываемый тип семантического слова') end; end; end;
begin
{ оформление экран } ClrScr; Gotoxy( 1,3);
WriteLnC Семантический анализ предложения "', SemFileName,'" (по плану "',
SemFileName, '.', SemFileExt,'") .' );
{ открытие файл с ПСД }
New( Sem, Init);
if not Sem^.SFOpen( SemFileName+'.'+SemFileExt) then begin
WriteLn(' Ошибки при открытии файла семантических данных.');
exit; end;
{ создание файла, в который будет записан результат семантического анализа } Assign( tf, SemFileName+'.'+ResFileExt); {$I-} Rewrite (tf); {$I+} i := lOResult; if i <> 0 then begin
WriteLn(' Ошибки при создании файла результатов семантических действий.');
exit; end;
{ цикл чтения строки ПСД и ее интерпретации } { выход из цикла по ошибке или при достижении конца файла } while Sem^.GetWord( gr.sw) and (sw.swt<>Seof) do SemAction( sw); { анализ причины завершения цикла } if (gr<>0) then begin { причина 1: GetWord=false }
case gr of
0: { все нормально};
1: WriteLn(' Файл семантических данных не открыт.'); 2: WriteLn(' Ошибки при получении семантического слова.') ; 3: WriteLn(' Чтение файла после исчерпания данных.'); 4: WriteLn(' Повторное сообщение об ошибке.');
end; end else if sw.swt=Seof then begin { причина 2: считаны все записи ПСД }
{ закрытие файла результата }
WriteLn(tf); :
WriteLn( tf,' Конец файла'); Close( tf );
WriteLn(' Семантический анализ благополучно завершен.');
WriteLn(' Сформирован файл "',SemFileName,'.',ResFileExt,'" - интерпретация плана
сем. действий.'); end
( закрытие файла с ПСД } Sem^.SFReset( 1 ); Dispose( Sem, Done ); end.