Ввод-вывод с помощью файлов целесообразно делать в случае большого объема вводимых (выводимых) величин, например, при работе с матрицами.
Пример. Написать программу умножения матриц a(m´n) и b(n´k) и выполнить ее для матриц
Решение. Пусть c – результирующая матрица. Тогда c имеет размеры m´k, и ее элементы вычисляются по формуле
Текст программы запишем в файл с именем pr8.pas, исходные данные – в файл pr8.dat, результаты – в файл pr8.res.
Программа.
program pr8;
type matr=array[1..20,1..20] of real;
var a,b,c:matr;
i,j,k,l,m,n:intrger;
fd,fr:text;
begin
assign(fd,¢pr8.dat¢);
assign(fr,¢pr8.res’);
reset(fd);
rewrite(fr);
read(fd,m,n,k);
for i:=1 to m do
for j:=1 to n do read(fd,a[i,j]);
for i:=1 to n do
for j:=1 to k do read(fd,b[i,j]);
for i:=1 to m do
for j:=1 to k do
begin
c[i,j]:=0;
for l:=1 to n do c[i,j]:=c[i,j]+a[i,l]*b[l,j]
end;
writeln(fr,¢произведение матриц a и b¢);
for i:=1 to m do
begin
for j:=1 to k do write(fr,c[i,j]:5:1);
writeln(fr)
end;
close(fr)
end.
Перед запуском программы на исполнение следует создать файл с именем pr8.dat и занести в него исходные данные в порядке чтения: сначала m, n, k, затем матрицу a и матрицу b. В нашем случае файл данных будет выглядеть следующим образом:
3 3 2
4 0 –1
7 –2 –4
5 7 9
-3 4
-4 –7
1 7
Записи.
Запись – это структура данных, состоящая из фиксированного числа компонентов, называемых полями записи, каждое поле именуется. В отличие от массива поля записи могут быть разных типов.
Задание типа записи:
type <имя>=record
<список имен полей с указанием типов>
end;
<список имен полей с указанием типов> представляет собой следующую конструкцию:
<поле 1>:<тип поля 1>;
<поле 2>:<тип поля 2>;
…………………………
<поле N>:<тип поля N>
В качестве примера можно рассмотреть тип записи birthday (день рождения), содержащий три поля с именами day, month и year (день, месяц и год).
type birthday=record
day:1..31;
month:1..12;
year:integer
end;
var a,b:birthday;
В этом примере переменные a, b содержат записи типа birthday. К каждому компоненту записи можно получить доступ, если указать имя переменной и затем через точку имя поля, например
a.day:=7;
b.year:=1993;
Турбо Паскаль допускает использование записи в качестве поля другой записи (иерархические записи), например
var c:record
name:string;
bd:birthday
end;
Доступ к полю year в этом случае:
c.bd.year:=1993;
Для упрощения доступа к полям записи может быть использованоператор присоединения:
with<переменная типа запись> do <оператор>;
Внутри оператора присоединения компоненты записи можно обозначать просто идентификаторами полей, например, вместо оператора
c.bd.day:=14;
можно записать
with c.bd do day:=14;
или
with c do with bd do day:=14;
или
with c,bd do day:=14;
Пример. Ввести дату своего рождения (число, месяц, год) и сегодняшнюю дату. Вычислить, сколько вам полных лет.
Решение. Вводятся две записи: bd (дата рождения) и d (сегодняшняя дата). Число полных лет z равно разности годов в случае, если дата рождения в текущем году (день и месяц) предшествует текущей дате; в противном случае число полных лет равно разности годов минус единица.
Программа.
program pr9;
type dat=record
day:1..31;
month:1..12;
year:integer;
end;
var bd,d:dat; z:integer;
begin
writeln(¢введите дату рождения¢);
with bd do
begin
write(¢число:_¢);
read(day);
write(¢_месяц:_¢);
read(month);
write(¢_год:_¢);
read(year);
end;
writeln(¢введите сегодняшнюю дату¢);
with d do
begin
write(¢число:_¢);
read(day);
write(¢_месяц:_¢);
read(month);
write(¢_год:_¢);
read(year);
end;
if (d.month>bd.month)or
(d.month=bd.month)and(d.day>=bd.day)
then z:=d.year-bd.year
else z:=d.year-bd.year-1;
writeln(¢число полных лет:_¢,z)
end.
10. Процедуры и функции
Процедуры и функции в Турбо Паскале (их еще называют подпрограммами) – это автономные программные единицы, которые спроектированы для реализации конкретных частных задач и могут быть многократно использованы в основной программе путем вызова.
Описание функции начинается с заголовка:
function <имя функции>(<список формальных параметров с указанием типов>):<тип результата>;
Список формальных параметров – это список аргументов данной функции, через которые осуществляется передача фактических параметров (реальных аргументов) в функцию. Каждый формальный параметр должен быть перечислен (в скобках после имени функции) с указанием своего типа (через двоеточие, как в обычном разделе описаний). При этом если какой-либо параметр принадлежит комбинированному типу (массив, матрица и т.д.), то этот комбинированный тип не может быть безымянным, но должен быть описан выше в разделе type.
После заголовка функции следуют разделы в том же порядке, что и в обычной программе, т.е. разделы описаний и раздел операторов. В разделе операторов должен хотя бы раз присутствовать определения результата функции, выглядящий как присвоение имени функции результата.
Замечание. Результат функции – всегда одиночная величина (не может быть комбинированного типа! – массивом, записью и т.д.)
Вызов и выполнение функции производятся путем указания в некотором выражении имени функции и далее в скобках списка фактических параметров (аргументов), которые должны соответствовать формальным, т.е. формальных и фактических параметров должно быть одинаковое количество, порядок перечисления формальных и фактических параметров должен быть один и тот же и типы соответствующих формальных и фактических параметров должны совпадать.
Пример. Даны x, y. Вычислить
где
Решение. Описываем f как функцию трех формальных аргументов – вещественных x, y и целого n. Для вычисления суммы нам потребуются две вспомогательные переменные – k и s. При вызове функции указываем фактические аргументы.
Программа.
program pr10;
var x,y,w:real;
function f(x,y:real;n:integer):real;
var k:integer; s:real;
begin
s:=0;
for k:=1 to n do s:=s+sin(k*x/10);
f:=s/sqrt(1+y*y)
end;
BEGIN
writeln(¢введите x,y¢);
read(x,y);
w:=(f(x*x,y,10)-f(1,x-y,15))/(1+f(y*y*y,cos(x),20));
writeln(¢w=¢,w)
END.
Описание процедуры также начинается с заголовка:
procedure <имя процедуры>(<список формальных параметров с указанием типов>);
С помощью параметров осуществляется передача данных в процедуру и передача результатов работы процедуры обратно в вызывающую программу. Таким образом, параметры процедуры могут быть входными и выходными. Входные играют роль аргументов функции, выходные – роль результатов, при этом в отличие от функции результатов может быть несколько, и они могут быть комбинированных типов.
В списке формальных параметров могут быть параметры-значения и параметры-переменные (перед последними ставится служебное слово var). При вызове процедуры параметры-значения передаются в процедуру по их значению, а параметры-переменные – по их имени. Основное отличие этих способов передачи параметров заключается в том, что присваивания значений параметру-переменной внутри процедуры одновременно выполняются и для соответствующей переменной внутри вызывающей программной единицы (основной программы, либо другой процедуры/функции), а при присваивании значений параметру-значению этого не происходит. Следовательно, выходные параметры (т.е. те, в которые записываются результаты работы процедуры) должны передаваться только по имени, т.е. быть параметрами-переменными (с пометкой var при описании). При вызове процедуры в качестве фактических параметров-переменных могут быть только переменные, в то время как в качестве фактических параметров-значений могут быть как переменные, так и выражения, и константы.
Вызов процедуры осуществляется с помощью оператора вызова процедуры, выглядящего как упоминание имени процедуры со списком фактических параметров, перечисленных в скобках через запятую:
<имя процедуры>(<список фактических параметров>);
с теми же условиями соответствия фактических параметров формальным, что и для функции.
Основное отличие вызова процедуры от вызова функции состоит в том, что вызов процедуры – это самостоятельный оператор, в то время как вызов функции происходит в рамках другого оператора, как правило, оператора присваивания (говоря точнее, в Турбо Паскале и вызов функции возможен в качестве самостоятельного оператора, но это выходит за рамки нашего курса).
Пример. Подсчитать куб матрицы размера 2´2. Умножение матриц оформить в виде процедуры.
Решение. Организуем процедуру prod с тремя параметрами-матрицами: входные a, b и выходная c, равная произведению a и b. При подсчете в основной программе матрицы b, равной кубу матрицы a, организуем вспомогательную матрицу r, равную квадрату матрицы a.
Ввод и вывод осуществляем с помощью файлов.
Программа.
program pr11;
type matr=array[1..2,1..2]of real;
var a,b,r:matr;
i,j:integer;
fd,fr:text;
procedure prod(a,b:matr;var c:matr);
begin
c[1,1]:=a[1,1]*b[1,1]+a[1,2]*b[2,1];
c[1,2]:=a[1,1]*b[1,2]+a[1,2]*b[2,2];
c[2,1]:=a[2,1]*b[1,1]+a[2,2]*b[2,1];
c[2,2]:=a[2,1]*b[1,2]+a[2,2]*b[2,2];
end;
BEGIN
assign(fd,¢pr11.dat¢);
assign(fr,¢pr11.res¢);
reset(fd);
rewrite(fr);
for i:=1 to 2 do
for j:=1 to 2 do read(fd,a[i,]]);
prod(a,a,r);
prod(a,r,b);
for i:=1 to 2 do
begin
for j:=1 to 2 do write(fr,b[i,j]:5:1);
writeln(fr)
end;
close(fr)
END.
Замечание. Переменная b означает разные вещи внутри разных программных единиц: внутри процедуры prod формальный входной параметр, а внутри основной программы – матрицу-результат. Такая ситуация в Турбо Паскале вполне допустима и адекватно распознается компьютером (в случае, когда один и тот же идентификатор по-разному описывается в разных программных единицах).
Дата добавления: 2016-09-06; просмотров: 1233;