Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Пособие Алгоритмизация и программирование.doc
Скачиваний:
57
Добавлен:
11.03.2015
Размер:
796.67 Кб
Скачать

26. Динамические переменные

Переменные, структура и тип которых определяются в разделе описаний блока (программы или подпрограммы), существуют и не изменяют своей структуры в течение всего времени работы блока. Такие переменные и связанные с ними структуры называются статическими.

Использование статических переменных и структур удобно не всегда. Иногда требуется, чтобы переменные возникали уже при выполнении программы или меняли свои размеры и структуру. Такие переменные и структуры называются динамическими.

Например, при решении задачи требуется сохранить в оперативной памяти слова вводимого текста, удовлетворяющие некоторому условию. Таких слов может не оказаться вовсе или это будут все слова текста. При использовании статических структур придется зарезервировать объем памяти для хранения структуры максимального размера. При этом память используется нерационально.

26.1. Ссылочный тип данных

В Паскале есть возможность создания динамических переменных с помощью переменных ссылочного типа.

Описание ссылочного типа:

Значением типа указатель является адрес переменной базового типа. Тип указатель занимает 4 байта (сегмент и смещение).

Пример 1. Описание переменных ссылочных типов.

Type t_ptr_real=^real;

t_vect=array[1..100] of char;

Varp1,p2:t_ptr_real; {указатель на вещественное число}

p_vect:^t_vect; {указатель на символьный массив}

Описанные переменные-указатели являются статическими, каждая из них занимает 4 байта. При описании переменные не инициализируются, поэтому их значения считаются неопределенными.

В ТР предопределен ссылочный тип pointer нетипизованный указатель. Его значением является адрес ячейки памяти.

Начиная с версии ТР7, в ТР реализован тип Pchar= ^Char.

Инициализация переменной ссылочного типа может быть выполнена с помощью оператора присваивания или с помощью подпрограмм выделения памяти.

Ссылочные типы совместимы по присваиванию, если их базовые типы тождественны или один из них является нетипизованным указателем. Существует предопределенная константа nil:pointer (пустой указатель). После присваивания р:=nilуказательpне ссылается ни на какую область памяти. Если переменная р1 уже инициализирована и р1nil, то после присваивания р2:=р1 обе переменные ссылаются на одну и ту же область памяти.

Тип Pchar, кроме того, совместим по присваиванию с символьным массивом и строковым типом.

26.2. Подпрограммы динамического распределения памяти

Создать динамическую переменную можно с помощью одной из следующих подпрограмм.

  1. Процедура New(varp: <указатель>) выделяет место в динамически распределяемой области памяти, называемой «кучей», для размещения переменной базового типа указателяpи начальный адрес присваивает переменнойp.

  2. Функция New(<имя ссылочного типа>):pointerвыделяет место в динамически распределяемой области памяти для размещения переменной указанного в качестве параметра типа и возвращает адрес выделенной области.

  3. Процедура GetMem(varp:pointer;n:word) выделяет в «куче» блок памяти размеромn, начальный адрес блока помещает вp. Еслир типизованный указатель, то значением второго параметра должен быть размер базового типа указателя. Для его определения удобно использовать функциюSizeOf(<имя типа><выражение>):word, которая возвращает размер своего параметра в байтах.

Если по какой-либо причине место для размещения переменной не может быть выделено, то происходит аварийный останов.

Функция MaxAvail:LongIntвозвращает размер максимального свободного блока в «куче». С ее помощью можно проверить, достаточно ли места для размещения динамической переменной. ФункцияMемAvail:LongIntвозвращает суммарный размер всех свободных блоков.

После окончания работы с динамической переменной память, занимаемая этой переменной, должна быть освобождена одной из процедур:

Dispose(varp: <типизованный указатель>)

или

FreeMem(var p: pointer; size:word).

Disposeосвобождает память, занимаемую переменной базового типа указателя р.FreeMemосвобождает блок памяти размеромsizeбайтов с начальным адресом р. В качестве параметраsizeдолжен быть указан размер динамической переменной. Каждому обращению к подпрограмме выделения памяти должна соответствовать процедура освобождения памяти.