
Inf : char; {в общем случае некоторый тип inf : t0 }
link: tр
end;
Представление стека
Стек- линейный последовательный список , в который доступ, включение и исключение элементов осуществляется только с одного конца, то естб доступна позиция-вершина стека. Последним пришел, первым ушел. причем указатель вышерасположенного элемента указывает на предыдущий элемент. Внешний указатель (указатель стека) должен указывать на верхний элемент стека.
Для организации и ведения стека должны быть предусмотрены два указателя: ТОР и К: К – для организации нового элемента и переприсваивания вершины, ТОР – для указания на вершину.
Var
top, к : Tр;
ch : char;
Для добавления элемента в стек необходимо:
образовать динамическую переменную по указателю К;
занести в её информационное поле нужную информацию;
в поле указателя нового элемента занести значение указателя ТОР;
указателю ТОР присвоить значение указателя К (т.е. новый адрес).
NEW(K);
k ^. inf := ch;
k ^. link := Tор;
top := k;
Для удаления элемента из стека достаточно:
прочитать информацию ;
в указатель Тор занести указатель удаляемого элемента.
ch := Top ^.inf;
Тор := Top ^. link;
Но в этом случае удаленный из стека элемент образует "мусор". Лучше удалить из памяти этот элемент, предварительно сохранив значение указателя Тор:
k := Тор; сохраним значение указателя вершины
Top := k ^. link; поменяем указатель вершины
Ch := k ^. inf; сохраним информацию (если нужно)
dispose (k); удалим из памяти отведенное ранее место.
Формирование стека с самого начала. Стек из N элементов:
Top := nil; объявить нулевую ссылку
while n > 0 do
begin
new(k); породить новый элемент
read (ch); ввести значение в информационное поле
k ^. inf := ch;
k ^ .link := Top; в поле указателя занести предыдущую ссылку
Top := k; объявить вершиной вновь созданную ссылку
n := n-1
end;
Выбор всех элементов стека
repeat
k := Top; запомним значение вершины для последующего удаления
Top := k ^ .link; в вершину занесем значение, на которое ссылалось предыдущее значение
ch := k ^. inf; прочитаем значение информационного поля удаляемой вершины стека
write (ch); выведем это значение
dispose (k); удалим элемент из памяти
until top = nil;
Представление очереди
Очередь линейная последовательность список в который все включения производятся в конце списка, а исключения в начале. Первый пришел, первый ушел.
для
идентификации организуются 2 указателя:
F-указатель головы, R-адресует хвост. Таким образом, для работы с очередью нужны три переменных типа "указатель".
Type
Tр = ^ Sр;
Sp = record
Inf : char;
Link : Tp;
End;
Var
f, k, r : Tp;
ch : char;
Удаление из очереди
очереди полностью эквивалентна операции удаления из стека
k := f;
f := k^ . link;
Ch := k^.inf;
Dispose (k);
Добавление в очередь
Операция добавления в очередь – это добавление после элемента, на который указывает R:
New(K); выделяем память для нового элемента
k^.inf := ch; заносим информацию в новый элемент
k^.link. := nil; заносим значение nil, т.к. этот элемент стал последним
r^.link := k; - в хвост записали адрес (ссылку) на созданный элемент
r := k; указатель на последний элемент (создали хвост)
Проверка очереди на пустоту осуществляется сравнением F с NIL.
If f<>nil then begin
K:=f;
F:=k.link;
Dispose(k);
G1:=g1-1
Добавление в кольцевую очередь:
procedure TForm1.Button7Click(Sender: TObject);
begin
randomize;
if q1=0 then // если первый элемент очереди
begin
new(r);
r.inf:=random(10);
r.link:=nil;
edit5.Text:=edit5.Text+inttostr(r.inf)+' ';
q1:=q1+1;
f:=r;
end
else
begin
New(K);
k.inf := random(10);
edit5.Text:=edit5.Text+inttostr(k.inf)+' ';
k.link:= f;
r.link := k;
r := k;
q1:=q1+1;
end;
edit6.text:=inttostr(q1);
end;
Дек (от англ. deque – double ended queue [кью]) – линейный последовательный список с двумя концами, в котором как включение, так и исключение элементов может осуществляться с любого из концов списка. Является сочетанием очереди и стека/
Частными случаями являются:
1). Дек с ограниченным входом (закрыт верхний участок пути);
2). Дек с ограниченным выходом(закрыт нижний участок пути).
Основные операции над деком – включение и исключение элементов.
Ведение динамических списков с помощью указателей
Простейшие связные списки — односвязный (один указатель), двусвязные (два указателя). В принципе может быть и больше указателей.
В односвязном списке каждый элемент состоит из двух полей: содержательного и поля указателя. Содержательное (информационное) поле хранит данные (в общем случае это запись). Поле указателя хранит адрес следующего элемента списка.
Type
Tр = ^ Sр;
Sp = record
inf : char; {inf : t0}
link : Tp;
end;
Var
nach, i, j, к : tp;
с :char;
Основные операции со списками.
Переход к следующему элементу.
Пусть i – указатель на текущий элемент списка.
Тогда
j := i.link; ‑ указывает на следующий элемент списка.
Поиск нужного элемента с начала списка.
Пусть хотим найти элемент со значением 'А'.
i := nach;
while (с <> 'A') and (i <> nil) do
begin
с := i.inf;
i := i.link;
end;
if с <> 'A' then writeln('нет элемента');
Включение в список после элемента с указателем I.
New(j); порождение элемента
j.inf := с; запись значения в информационное поле элемента списка
j.link := i.link; ссылка на следующий после i должна храниться в j
i.link := j; а в i должна храниться ссылка на j
Удаление из списка после элемента с указателем I.
j := i.link; если этого не сделать – появится "мусор" в НЕАР
i.link := j.link;
с := j.inf; {убрать этот оператор, если информацию сохранять не надо}
dispose (j);
Добавлять перед элементом или удалять сам текущий элемент невозможно, т.к. связь с предыдущим элементом отсутствует.
Однако простой прием позволяет преодолеть эту трудность. Добавление перед:
добавить после элемента с указателем I, a затем поменять местами информационные части добавленного и предыдущего элементов.
New(j);
j.link := i.link;
i.link := j;
j.inf := i.inf;
i.inf := c;
Удаление самого элемента: поменять местами следующий и текущий элементы списка, а затем удалить следующий элемент.
j := i.link; нашли следующий
с := j.inf; запомнили следующий (если нужно)
i.inf := с; записали в предыдущий
i.link := j.link; сменили связь
dispose (j);
Операция удаления возможна, когда удаляемый элемент не последний в списке.
16. основные понятия модульного программирования
Основные понятия модульного программирования
Модульное программирование включает методы разработки сложных программ путем их декомпозиции, в том числе выбор типов модулей и особенности функционирования каждого из них.
Модуль – это относительно самостоятельный фрагмент программы для функционально законченной обработки данных. Разбиение программы повышает надежность, наглядность и живучесть программы.
Сейчас под модулем понимают независимо хранимые, независимо компилируемые и тестируемые программные единицы со строго определенными интерфейсами, которые могут объединяться в различных сочетаниях.
Структура модуля
В языке ОР модуль (unit) по определению считается отдельной программой. В самом общем виде модуль представляет собой совокупность программных ресурсов, предназначенных для использования другими модулями и программами. Важно понимать, что модуль сам по себе не является выполнимой программой – его объекты ИСПОЛЬЗУЮТСЯ другими программными единицами.
Все программные ресурсы модуля можно разбить на две части: объекты, прямо предназначенные для использования другими программами или модулями, и объекты рабочего характера. В соответствии с этим модуль имеет заголовок и две основные части: интерфейс и реализацию.
В интерфейсной части модуля сосредоточены описания объектов, доступных из других программ; такие объекты называют видимыми вне модуля. В части реализации помещаются рабочие объекты, называемые также невидимыми или скрытыми.
Заголовок модуля состоит из служебного слова unit и следующего за ним идентификатора, являющегося именем модуля. Заголовок завершается символом " ; ".
Интерфейсная часть начинается со служебного interface, за которым следует совокупность обычных описаний.
Часть реализации начинается служебным словом implementation, за которым следуют описания скрытых объектов. Завершает модуль, как и программу, служебное слово end с точкой.
Кроме перечисленных частей, модуль может содержать две части, которые чаще всего отсутствуют:
- раздел инициализации - initialization, предназначенный для установки начальных значений переменных модуля перед его использованием. Этот раздел следует после раздела реализации, и содержит последовательность операторов, которые исполняются до передачи управления основной программе и обычно используются для подготовки ее работы.
- завершающий радел – finalization, предназначен для завершающей части модуля, в которой указываются операторы, выполняющиеся уже после работы основной программы.
Если несколько модулей содержат инициирующие части, то эти части выполняются последовательно друг за другом в порядке перечисления модулей в строке спецификации Uses главной программы.
unit UnitName;
interface
Описания видимых объектов
implementation
Описания скрытых объектов
initialization
Операторы инициализации
finalization
Операторы завершающей части
end.
Подпрограммы в модулях
Заголовок подпрограммы содержит всю информацию, необходимую для ее вызова: ее имя, количество и типы параметров и для функций тип результата. в интерфейсной части модуля должны быть представлены только заголовки процедур и функций, видимые (доступные) для других программ (аналогично предварительным описаниям, но без служебного слова forward), а их полные описания будут содержаться в разделе реализации.
модификация модуля никак не отразится на использующих его программах, если интерфейс модуля при этом останется неизменным.
Компиляция модуля
заголовок модуля несет семантическую нагрузку. компилятор должен каким-то образом отыскать коды этих модулей, чтобы подключить их к компилируемой программе. Поэтому имя файла, содержащего исходный текст модуля, должно совпадать с именем этого модуля.
компилятор ищет файл модуля с именем, заданным в uses-спецификации, и связывает его с кодом программы.фактически задаются не имена модулей, а имена файлов,
создания модуля
Выбрать в пункте меню File команду New \Unit.
Сохранить в файле, имя которого совпадает с именем модуля.
При необходимости отладки созданного модуля, его текст можно открыть с помощью команды View \ Units или комбинацией клавиш Ctrl + F12.
Если некоторый модуль использует объекты другого модуля, то такая спецификация должна следовать сразу после служебного слова interface. в данной программе считаются известными все описания из интерфейсной части подключенного модуля.
1. Идентификаторы интерфейсной части используемого модуля частично пересекаются с идентификаторами использующей программы. В этом случае действует следующее правило видимости имен: интерфейсные идентификаторы модуля, указанного первым в uses-списке, образуют самый внешний блок программы; интерфейсные идентификаторы второго модуля образуют блок, вложенный в первый блок. Uses A, B;
идентификаторы модуля А
идентификаторы модуля В
идентификаторы программы
2.случаи косвенных использований. Например, имеется два модуля :
Unit A; interface
end. |
Unit B ; interface uses A ; end. |
необходимо указать только модули, непосредственно используемые в программе. Program P; Uses B; end.
3.Схема использования модулей может образовывать древовидную структуру любой сложности, но при этом недопустимо явное или косвенное обращение модуля к самому себе
Unit A; interface uses B; end. |
Unit B ; interface uses A ; end. |
Типы модулей в Delphi
распространенным типом модуля в Delphi является форма – модуль со связанным с ним окном.
Большинство типовых модулей в репозитории (архиве) содержат заготовки для создания диалоговых окон.
Модули данных имеют связанные с ними окна, но эти окна никогда не появляются на экране.
Модули динамических библиотек предназначены для создания широко используемых в Windows динамически связываемых библиотек DLL . DLL служат универсальным средством согласования подпрограмм, написанных на разных языках программирования.
Пакеты – это особым образом откомпилированные DLL, оптимизированные для совместного использования Delphi-программами или средой Delphi, или и программами и средой. В отличие от DLL, пакеты могут хранить и передавать программе типы (включая классы) и данные.
Модули потоков предназначены для реализации так называемых потоков команд – фрагментов программы, которые исполняются параллельно с другими фрагментами, разделяя с ними время процессора и остальные системные ресурсы.