Проверка наличия требуемого объема памяти в HEAP-области.
Предотвращение ошибочных ситуаций при распределении динамической памяти
Перед использованием стандартных процедур распределения динамической памяти необходимо проверить наличие требуемого объема памяти в HEAP -области.
FUNCTION CHECK(VAR P:POINTER; SIZE:WORD): BOOLEAN;
BEGIN
CHECK:=TRUE;
IF SIZE<=MAXAVAIL THEN
GETMEM(P,SIZE)
ELSE
CHECK:=FALSE;
END;
Функция возвращает значение TRUE, если запрашиваемый размер памяти меньше или равен размеру наибольшего непрерывного участка памяти в HEAP -области (функция MAXAVAIL), иначе – FALSE.
2. Использование функции указателя HeapError – стандартной функции, адрес которой при запуске программы содержит переменная HeapError; возвращает 0, что приводит к останову программы по ошибке периода счета с кодом 203.
Можно переопределить эту функцию и таким образом блокировать останов программы, для чего необходимо написать собственную функцию и поместить ее адрес в указатель HeapError.
{$F+}
FUNCTION HEAPFUNC(SIZE:WORD): INTEGER;
BEGIN
HEAPFUNC:=1;
|
|
END;
{$F-}
FUNCTION CHECK(VAR P: POINTER; SIZE: WORD): BOOLEAN;
VAR
OLDHEAPER: POINTER;
BEGIN
OLDHEAPER:= HEAPERROR;
HEAPERROR:=ADDR(HEAPFUNC);
GETMEM(P, SIZE);
HEAPERROR:= OLDHEAPER;
CHECK:= (P<>NIL);
END;
Функция HEAPFUNC принудительно возвращает указатель NIL, если невозможно выделить достаточно динамической памяти для распределения данных.
Функция CHECK пытается разместить динамическую переменную в памяти и возвращает значение TRUE, если операция выделения памяти прошла успешно.
Данный способ локализации ошибок распределения памяти в HEAP -области является наиболее предпочтительным.
Динамическим массивом ее я вания за иской памятинеобходимое для размещения требуемой переменной. называется массив, память для которого выделяется во время выполнения программы, обращение к области памяти осуществляется через указатель на ее начало (указатель может являться статической переменной, описанной и имеющей имя); область памяти, выделяемой для массива, имени не имеет, и доступ к ней происходит по адресу, содержащемуся в указателе.
Таким образом, в случае работы с динамическим массивом программист должен самостоятельно заботиться о резервировании памяти.
Необходимость использования средств работы с динамической памятью при обработке массивов возникает в случаях, когда статическая реализация неэффективна (например, размеры массивов заранее неизвестны, а резервирование памяти максимально возможного объема нерационально). При этом суть понятия массива сохраняется, т. е. массив – это совокупность однотипных элементов, которые расположены в определенном порядке и различаются индексами; над каждым элементом массива возможны любые операции, допускаемые типом элементов.
|
|
Перечисленные свойства достаточно просто моделируются средствами динамической памяти, которая является, фактически, единственной возможностью обработки массивов данных большой размерности, таких, которые настолько велики, что не могут быть размещены в сегменте данных размером в 64 Кбайт. Только в динамической памяти можно создать массив, размер которого заранее не определён.
Один из возможных вариантов получения динамического двумерного массива размерности n на m:
type
mas = array [1..1] of integer;
pmas = ^mas;
matr = array [1..1] of pmas;
pmatr = ^matr;
var
a: pmatr;
n, m: integer;
begin
readln(n, m);
GetMem (a, n*sizeof(pmas));
for i:=1 to n do
GetMem (a^[i], m*sizeof(integer));
...
{ обращение к отдельному элементу имеет вид a^[i]^[j] }
...
for i:=1 to n do
FreeMem (a^[i], m*sizeof(integer));
FreeMem (a, n*sizeof(pmas));
end.