ВУЗ: Томский государственный университет систем управления и радиоэлектроники
Категория: Учебное пособие
Дисциплина: Проектирование информационных систем
Добавлен: 21.10.2018
Просмотров: 10765
Скачиваний: 8
71
Рис.
4.12
—
Фиксированные
данные
абстрактного
типа
Однако
такая
организация
данных
имеет
существенные
недостатки,
так
как
компоненты
любой
структуры
видны
во
всех
процедурах,
которые
используют
эти
структуры.
Програм-
мист
должен
изменять
структуры
осторожно
с
помощью
опре-
деленных
операторов
и
не
вводить
кажущиеся
«безвредными»
операторы
для
непосредственного
обращения
к
данным.
Исполь-
зуемый
тип
оператора
может
вызвать
неприятности,
если
каждая
компонента
не
будет
заменена
соответствующим
образом.
Несмотря
на
отмеченные
недостатки,
данный
способ
мо-
жет
оказаться
единственно
возможным
для
некоторых
языков
программирования.
4.3.2.2 Размещение указателей
Используя
переменные
типа
указатель,
можно
построить
конструкцию,
близкую
к
фиксированным
данным
абстрактного
типа.
Предполагается,
что
указатель
указывает
на
область
памя-
ти,
а
формат
этой
памяти
определяется
с
помощью
базирован-
ных
переменных
абстрактного
типа.
Используя
данные
абст-
рактного
типа,
пользователь
определяет
данные
как
перемен-
ную
—
указатель
и
вызывает
процедуру
для
размещения
дан-
Модуль,
использующий
данные
Модуль,
определяющий
данные
Элементы
TOPOFSTACK
Элементы
1
2
3
4
5
6
…
100
TOPOFSTACK
1
2
3
4
5
6
…
100
72
ных
и
обращения
к
этой
структуре.
Для
стека
это
может
быть
в
виде:
declare
STACK POINTER;
call
STACK_INITIALIZATION(STACK);
В
этом
случае
процедура
STACK_INITIALIZATION
должна
быть
вызвана
явным
образом
для
того,
чтобы
разместить
стек
в
памяти
(рис.
4.13).
Процедура
STACK_INITIALIZATION
должна
иметь
сле-
дующую
структуру:
STACK_INITIALIZATION: procedure(X);
declare X POINTER;
declare 1 STACK BASED(X),
/* X –
указывает на стек */
2 ENTRIES(100) FIXED,
2 TOPOFSTACK FIXED;
ALLOCATE STACK SET(X);
TOPOFSTACK = 0;
end
;
Рис.
4.13
—
Размещение
указателей
Модуль,
использующий
данные
STACK
Модуль,
определяющий
данные
Элементы
TOPOFSTACK
1
2
3
4
5
6
…
100
73
Только
в
этой
процедуре
известна
структура
данных,
на
которые
ссылается
указатель
STACK
,
поэтому
довольно
сложно
изменить
эту
структуру
за
пределами
процедуры.
Для
того
чтобы
определить
функции
обращения
к
стеку,
можно
использовать
операторы
ENTRY
.
Таким
образом,
вся
конструкция
STACK
в
целом
имеет
следующий
вид:
STACK: procedure;
declare X POINTER;
declare 1 STACK BASED(X);
2 ENTRIES(100) FIXED,
2 TOPOFSTACK FIXED;
/*
разместить стек */
STACK_INITIALIZATION: ENTRY(X);
...
/*
поместить элемент в стек */
PUSH: procedure(X,
элемент);
...
return;
/*
извлечь элемент из стека */
POP: procedure(X,
элемент);
...
return;
...
end;
Рассмотренный
способ
удовлетворяет
основным
предъяв-
ляемым
требованиям:
имена
структур
и
их
представления
разъ-
единены,
все
операции
со
стеком
сосредоточены
внутри
одной
процедуры
(только
из
этой
процедуры
можно
обращаться
к
данным).
Однако
данному
способу
присущ
тот
же
недостаток,
что
и
первому.
С
его
помощью
действительно
строятся
данные
абстрактного
типа,
однако
во
многих
современных
языках
не
существует
ограничений,
которые
гарантировали
бы,
что
к
этим
данным
никто
не
обращается,
т.е.
невозможно
запретить
программисту
напрямую
обратиться
к
данным,
на
которые
ссы-
лается
указатель.
74
4.3.2.3 Защита данных от несанкционированного доступа
Этот
способ
организации
данных
подобен
предыдущему,
но
содержит
средства
контроля
для
определения
некорректных
обращений.
Для
определения
данных
этого
типа
добавляется
атрибут
ENVIRONMENT
(среда,
окружение).
declare
X ENVIRONMENT(STACK);
Для
пользователя
Х
—
это
стек,
к
которому
можно
обра-
щаться
из
процедуры
STACK
(например,
с
помощью
функций
POP
,
PUSH
,
EMPTY
)
аналогично
тому,
как
если
бы
Х
было
дей-
ствительное
число
и
им
можно
было
бы
оперировать,
используя
операции
сложения
или
умножения.
Пользователь
не
знает,
как
составлен
стек,
и
не
имеет
доступа
к
его
внутренней
структуре
так
же,
как
и
большинство
программистов
находятся
в
неведе-
нии
относительно
того,
каким
образом
величина
с
плавающей
точкой
записывается
в
память
ЭВМ.
Стек
объявляется
компи-
лятором
как
переменная-указатель,
но
при
этом
накладываются
дополнительные
ограничения:
1)
обработка
стека
Х
происходит
в
процедуре
FUNCTION
в
модуле
с
именем
STACK
;
2)
описание
стека
Х
может
находиться
только
в
операторе
REP
(представление
для
переменной)
в
модуле
STACK
;
3)
любые
другие
обращения
к
стеку
Х
запрещены.
С
точки
зрения
пользователя,
данные
абстрактного
типа
не
должны
отличаться
от
других
переменных
в
программе.
Од-
нако
имеется
одно
существенное
различие
между
переменными
типа
FIXED
и
BLIPPO
.
Переменная
типа
FIXED
размещается
в
памяти,
когда
начинает
выполняться
процедура
(или
блок),
со-
держащая
объявление
переменной,
и
освобождает
память,
когда
процедура
(блок)
завершится.
А
для
переменной
типа
BLIPPO
должна
быть
выделена
постоянная
память.
Это
может
привести
к
двусмысленной
ситуации.
Так
как
одна
из
целей
применения
данных
абстрактного
типа
заключается
в
расширении
типов
данных
для
прикладных
задач,
различие
между
типами
данных,
генерируемых
компилятором,
и
данных,
созданных
пользовате-
лями,
может
вызвать
недоразумения.
Следовательно,
одной
из
75
задач
проектирования
с
использованием
данных
абстрактного
типа
должно
быть
автоматическое
размещение
таких
данных
при
их
использовании,
так
чтобы
не
было
различий
в
стратегии
использования
памяти
для
указанных
двух
типов
данных.
Для
того
чтобы
использовать
автоматическое
распределе-
ние
памяти,
переменная
Х
инициируется
при
вызове
модуля
STACK
.
По
существу,
компилирование
объявления
ENVIRON-
MENT
эквивалентно
следующей
записи.
declare
X POINTER INITIAL(STACK);
При
первоначальном
обращении
к
модулю
STACK
рас-
пределяется
память
для
стека
Х
и
возвращается
ее
адрес
в
пере-
менную-указатель.
Модуль,
в
котором
происходит
обработка
стека
Х,
имеет
вид:
STACK: ABSTRACTION;
REP 1 STACK[X], /*
имя параметра стека*/
2 ENTRIES(100) FIXED,
2 TOPOFSTACK FIXED;
/*
разместить стек */
/*
присвоить начальные значения */
TOPOFSTACK = 0;
PUSH: function(X,
элемент);
...
end;
POP: function(X,
элемент);
...
end;
...
end
;
Такую
процедуру
легко
написать
на
современных
языках,
учитывая
следующее.
Начало
процедуры
ABSTRACTION
предназначено
для
размещения
данных
абстрактного
типа
и
присвоения
им
на-
чальных
значений;
однако
действительным
распределением
па-
мяти
автоматически
занимается
компилятор.
Это
делается
для
сохранения
совместимости
с
элементарными
типами
данных,
такими,
как
FIXED
и
REAL
.