До его выполнения значения переменных


До его выполнения значения переменных "а" и "b" не определены, после выполнения имеем "а = 9". После выполнения следующего оператора значение "b" становится равным "81", после выполнения последнего оператора получаем "а = 6561", а значение "b" по-прежнему равно "81".
В этом примере процедура послужила по существу средством сокращения записи, позволив избежать трехкратного включения "тела" в программу, хотя мы вполне могли бы написать:
begin integer a, b; L: а := 3 3; b := а а; а := b b end
В случае более сложного, чем в этом примере, тела длина программы значительно увеличилась бы.
Метод "подстановки вместо обращения к процедуре соответствующим образом преобразованного тела процедуры", однако, невозможен, если процедура является рекурсивной, т. е. сама может вызывать себя. Такая процедура действительно расширяет выразительную силу языка программирования.
Проиллюстрируем использование рекурсивной процедуры на простом примере. Общий наибольший делитель (ОНД) двух натуральных чисел определяется так:

  1. если числа равны, то ОНД равен этому общему значению;
  2. если числа не равны, то ОНД равен общему наибольшему делителю меньшего из исходных чисел и их разности.

Иначе говоря, если ОНД не определяется тривиально (первый случай), то задача его нахождения заменяется отысканием ОНД для двух чисел с меньшими значениями.
(В следующей ниже программе спецификация "value v, w;" может быть пропущена читателем как не относящаяся по существу к обсуждаемому вопросу; она указывает, что для тела процедуры представляют интерес лишь числовые значения перечисленных параметров, задаваемые при обращении к процедуре).
begin integer a; procedure ОНД (u, v, w); value v, w; integer u, v, w; if v = w then u := v else begin if v < w then ОНД (u, v, w - v) else ОНД (u, v - w, w) end; ОНД (a, 12, 33) end
(B этом примере использована более сложная форма условного оператора, а именно:

Читателю предоставляется проследить за последовательностью



Читателю предоставляется проследить за последовательностью


if условие then оператор 1 else оператор 2
что означает: если "условие" удовлетворяется, то выполняется "оператор 1", а "оператор 2" пропускается; если "условие" не удовлетворяется, то пропускается "оператор 1", а выполняется "оператор 2".)
Читателю предоставляется проследить за последовательностью обращений к процедуре ОНД и убедиться, что переменная "а" получает значение "З". Необходимо также осознать, что (динамическая) схема обращений зависит от заданных параметров, и поэтому метод подстановки из предыдущего примера - замещение обращения к процедуре телом процедуры - привел бы здесь к трудностям.
Теперь мы составим программу умножения матрицы на вектор, в которой:

  1. порядок вычисления М произведений скаляра на скаляр точно определен (строки матрицы просматриваются слева направо);
  2. N строк матрицы могут обрабатываться параллельно. (Там, где мы не хотим ограничиваться только целочисленными значениями, использован описатель "real" вместо описателя "integer"; кроме того, мы ввели двумерный массив, что, вероятно, у читателя не вызовет затруднений.)

Предполагается, что перед входом в этот блок целые переменные "М" и "N" получают положительные значения.
begin real array матрица[1 : N, 1 : M]; real array вектор[1 : M]; real array произведение[1 : N]; procedure умножстроки(k); value k; integer k; begin if k > 0 then
parbegin
begin real s; integer j; s := 0; for j := 1 step 1 until M do
s := s + матрица[k, 3] вектор[jl; произведение[k] := s end; умножстроки(k - 1) parend
end; . . . . умножстроки(N); . . end

Содержание раздела






Содержание раздела