Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Конструирование программ.doc
Скачиваний:
12
Добавлен:
05.05.2019
Размер:
12.37 Mб
Скачать

3.1.2.1. Формальные параметры как массивы с фиксированными размерами

В данном примере (рисунок 3.1) для описания типов параметров используется тип Massiv с фиксированной размерностью массива.

Рисунок 3.1 – Передача массива в подпрограмму

3.1.2.2. Формальные параметры как массивы со «свободными» размерами

Существует несколько возможностей передавать массивы в подпрограмму, не указывая их размеры. В языке Object Pascal для этого можно использовать функции low, high и sizeof.

Использование функций low, high и sizeof в консольном приложении требует подключения модуля SysUtils.

Описание размеров фактического массива должно начинаться с 0.

Использование функций low и high для определения размера массива в подпрограмме приведено на рисунке 3.2.

Функции low и high возвращают соответственно наименьшее и наибольшее значение индекса массива.

Рисунок 3.2 – Использование функций low и high

Для лучшего понимания и правильного использования этих функций удалите комментарии в отладочных операторах программы (рисунок 3.2).

Использование функции sizeof для определения размера массива в подпрограмме приведено на рисунке 3.3.

Функция sizeof возвращает размер данных в байтах.

Рисунок 3.3 – Использование функции sizeof

Для лучшего понимания и правильного использования функции sizeof удалите комментарии в отладочных операторах программы (рисунок 3.3).

3.1.2.3. Определение наименьшего/наибольшего значения массива

Рассмотрим процедуру minmax (рисунок 3.4), которая вычисляет минимальное или максимальное значение в одномерном массиве x и определяет номер этого значения в массиве.

Параметры процедуры minmax

Входные:

x – исходный массив,

compare – наименование функции сравнения (получает значение less или more);

Выходные:

minmaxElement – значение минимального/максимального элемента массива,

minmaxNumber – номер минимального/максимального элемента.

Функция сравнения less возвращает значение истина, если значение первого параметра меньше значения второго параметра.

Функция сравнения more возвращает значение истина, если значение первого параметра больше значения второго параметра.

Процедурный тип соответствующий этим функциям имеет вид:

MinMaxFunc = function (first, second: integer):boolean;

Спецификации функций less и more должны содержать ключевое слово far («дальний вызов»). Это указание необходимо компилятору для правильной генерации исполняемой программы.

Пусть в операторе вызова процедуры minmax в качестве наименования функции сравнения передается less.

Параметр minmaxElement будет получать значение элемента массива x[i], если x[i] меньше текущего значения этого параметра.

Таким образом, после завершения цикла сравнений параметр minmaxElement будет иметь значение наименьшего элемента массива, а параметр minmaxNumber – значение номера этого элемента.

Аналогично будет выполняться процедура minmax, если в качестве наименования функции сравнения передается more. В этом случае параметр minmaxElement будет получать значение элемента массива x[i], если x[i] больше текущего значения этого параметра. В результате minmaxElement будет иметь значение наибольшего элемента массива, а параметр minmaxNumber – значение номера этого элемента.

Результаты вызова процедуры minmax приведены на рисунке 3.5.

Рисунок 3.4 – Пример передачи наименования подпрограммы как параметра

Рисунок 3.5 – Результат работы процедуры minmax

Советы профессионала

Проверяйте ситуацию ВЫХОД ЗА ПРЕДЕЛЫ МАССИВА!

  • Установите автоматическую проверку выхода за пределы массива

В меню Project выберите пункт Options (условия) и в открывшемся окне Project Options (рисунок 3.6) установите галочку для автоматической проверки выхода за пределы массива – Compile/Range checking.

Если в процессе работы программы происходит выход за пределы массива, то выполнение будет прервано и выдано сообщение об ошибке. Таким образом, в процессе отладки программы Вы будете проинформированы о возникновении этой ситуации и сможете устранить ее причину.

Рисунок 3.6 – Установка свойства Range checking для проверки выхода за пределы массива

  • Пример. Поиск в массиве

Рассмотрим реализацию алгоритма поиска наименьшего номера K элемента массива (A: array[1..N] of integer), значение которого равно заданному X: .

Вариант 1

i:=1;

while (A[ i ]< >X) and (i <= N) do

i:=i+1;

if A[ i ] = X then

K:=i

else

. . . {элемент не найден};

Этот, очевидный на первый взгляд, код содержит фатальную ошибку.

Пусть i = N и A[ i ]< >Xв этом случае условие продолжение цикла истинно. Тогда i = i + 1 = N+1 и при вычислении выражения A[ i ]< >X в заголовке цикла происходит выход за пределы массиваA[ i ] A[N+1]!

Надеюсь, Вы легко исправите заголовок цикла так, чтобы исключить выход за пределы массива.

Вариант 2

Исключим из заголовка цикла проверку A[ i ]< >X. Вместо этого будем использовать логическую переменную Found.

i:=1;

Found := false; // элемент не найден

while (not Found) and (i <= N) do

if A[ i ] = X then

Found := true // элемент найден

else

i:=i+1;

if Found then

K:=i

else

. . . {элемент не найден};

Добавление логической переменной Found сделало код безопасней, но добавило ему сложность – три проверки на один шаг цикла:

1 – i <= N?

2 – (not Found) and (i <= N) = true ?

3 – A[ i ] = X ?

Это, конечно, далеко не лучший вариант поиска!

Вариант 3 – поиск «с барьером»

Увеличим размер массива A на 1A: array[1..N+1] of integer;

Присвоим элементу A[N+1] значение X. A[N+1] – это «барьер».

A[N+1] := X;

i:=1;

while (A[ i ]< >X) do //цикл завершается всегда

i:=i+1;

if i <= N then // цикл завершился при i <= N – элемент найден

K:=i

else

. . . {элемент не найден};

Не продолжайте обработку массива после того, как результат получен

Пусть переменная Found принимает значение true, если в массиве есть хотя бы один элемент больше 0, иначе – false

Вариант 1

Found:= false;

for :=1 to N do begin

if A[i]>0 then

Found:= true; // элемент найден, но цикл продолжается!

end;

if Found then

{элемент найден}

else

{нет такого элемента в массиве};

Вариант 2

Found:= false;

for :=1 to N do begin

if A[i]>0 then begin

Found:= true; // элемент найден,

break; // выход из цикла!

end;

end;

if Found then

{элемент найден}

else

{нет такого элемента в массиве};