
- •Глава 7. Структурированные типы данных
- •7.1. Массивы
- •7.1.1. Одномерный массив Объявление массива.Перед использованием массив, как и любая переменная, должен быть объявлен в разделе объявления переменных. В общем виде объявление массива выглядит так:
- •Вывод массива. Под выводом массива понимается вывод на экран значений элементов массива. Вывод элементов одномерного массива на экран.
- •1 9 5
- •6 9 7
- •Ввод двумерного массива
- •Описание типа множество
- •Операции над множествами
- •3.4. Адресный тип данных
1 9 5
6 9 7
Совпадение с элементом номер 7. Выполнено 2 сравнения.
ДВУМЕРНЫЕ МАССИВЫ
Исходные данные для решения многих задач можно представить в табличной форме. Например, таблица результатов производственной деятельности нескольких филиалов фирмы, таблица коэффициентов системы линейных уравнений и т.д. Для подобных случаев язык Раscаlпредоставляет структуру данных - двумерный массив. Операции, предназначенные для обработки таких массивов, включают:
ввод
поиск
поиск
выбор нужных элементов массива
сортировку
преобразование в виде поворота или зеркального отражения относительно какой – либо оси симметрии.
Объявление двумерного массива.
Описание двумерного массива выглядит следующим образом
имя: array [нижняя граница индекса1.. верхняя граница индекса1,
нижняя граница индекса2 .. верхняя граница индекса2] of тип;
где имя - имя массива;array- слово языка Равсаl, показывающее, что описываемый элемент данных - массив;
нижняя граница индекса1, верхняя граница индекса1,
нижняя граница индекс, верхняя граница индекса2 -константы или выражения типаinteger, определяющие диапазон изменения индексов и, следовательно, число элементов массива;
тип -тип элементов массива.
Значения элементов двумерных массивов вводят и выводят на экран, как правило, по строкам, т. е. сначала все элементы первой строки, затем второй и т. д. Это удобно выполнять при помощи вложенных инструкций for. Первый индекс определяет номер строки, второй - номер столбца.
В памяти компьютера двумерные массивы хранятся по строкам.
Описание двумерного массива осуществляется одним из следующих
способов
а) с помощью типизированной переменной:
type
mar =array [1..5] of byte;
var
a:array [1..5] of mar;
б) в разделе описания переменных
a:array [1..5, 1..5]ofinteger;
Ввод двумерного массива
Ввод массива с клавиатуры: Фрагмент программы имеет вид.
for i:=1 to n do
for j:=1 to m do
read(a[i,j]);
Ввод массива помощью типизированных констант. Фрагмент программы имеет
const
d : array [1..3, 1..3] of integer = ((-5,8,5),
(0,7,-8),
(1,4,8));
Ввод массива спомощью датчика случайных чисел. Фрагмент программы
имеет вид.
for i:=1 to 10 do
for j:=1 to m do
begin
a[i,j]:=random (20);
write(a[i]:5);
end;
Вывод двумерного массива
1) Вывод элементов массива в строку на экране
write(‘Вывод элементов двумерного массива ’)
for i:=1 to n do
for j:=1 to m do
writeln (a[i,j]);
2) В матричной форме
for i:=1 to n do
Begin
for j:=1 to m do
write (a[i,j]);
Writeln;
Ошибки при использовании массивов
При использовании массивов наиболее распространенной ошибкой является превышение индексом значения выражения верхней границы индекса указанной при объявлении массива. Если в качестве индекса используется константа и ее значение превышает верхнюю границу, то такая ошибка обнаруживается на этапе компиляции.
Если при обращении к элементу массива в качестве индекса используется переменная или выражение, то возможно возникновение ошибки времени выполнения программы (run time еггог).
В программы, в которых возможны ошибки времени выполнения вследствие неправильного ввода исходных данных, следует добавлять инструкции проверки вводимых данных.
Примеры программ с двумерными массивами.
Пример7_7. Ввод и вывод элементов двумерного массива.
Program prog8;
uses wincrt;
const
n=4;m=4;
var
k:real;
i,j:integer;
a:array[1..n,1..m] of integer;
begin
k:=20;
randomize;
for i:=1 to n do
begin
for j:=1 to m do
a[i,j]:= random(k);
end;
for i:=1 to n do
begin
for j:=1 to m do
begin
write(' ',a[i,j]:2.1);
end;
writeln;
end;
end.
Пример7_8. вычисление суммы элементов двумерного массива.
Program prog9;
uses Wincrt;
const
n=4;
m=4;
var
i,j:byte;
a:array[1..n,1..m] of integer;
s,k:byte;
begin
k:=20;
s:=0;
randomize;
for i:=1 to n do
begin
for j:=1 to m do
a[i,j]:=random(k);
end;
for i:=1 to n do
begin
for j:=1 to m do
if a[i,j]>0 then s:=s+a[i,j];
end;
for i:=1 to n do
begin
for j:=1 to m do
begin
write(' ',a[i,j]:2);
end;
writeln;
end;
write(s:2);
end.
Пример7_9. Суммирование матриц. Фрагмент программы, реализирующий суммирование:
for i:=1 to n do
begin
for j:=1 to m do
begin
c[i,j]:=a[i,j]+b[i,j];
{Можно a[i,j]:=a[i,j]+b[i,j]}
end;
end;
Пример7_10. Умножение вектора на матрицу. Результатом будет двумерный массив.
program progn;
uses Wincrt;
const
n=4;
m=4;
var
i,j:byte;
a:array[1..n,1..m] of integer;
b:array[1..n] of integer;
s,k:byte;
{ аналогично предыдущей }
begin
for i:=1 to N do
read(b[i]);
for j:=1 to m do
begin
s:=0;
for i:=1 to n do
begin
read(a[i,j]);
s:=s+b[i]*a[i,j]; {выполнение
умножения}
end;
c[j]:=s;
end;
write(s);
end.
Пример7_11. Вычисление произведения всех элементов массива.
Program lupa3;
Uses WinCrt;
const
a:array[1..4,1..4] of integer=((4,2,-3,-6),
(1,8,3,2), {Ввод с помощью}
(1,4,98,3), {типизированной
константы}
(3,1,1,1));
var
p,i,j:integer;
begin
writeln(‘ В двумерном массиве вычислить произведение’);
writeln(‘ всех элементов массива.’);
writeln (‘== Дана матрица==’);
for i:=1 to 4 do
begin
for j:=1 to 4 do
write(‘ ‘,a[i,j]:3);
writeln;
end;
p:=1;
for i:=1 to 4 do
for j:=1 to 4 do
begin
p:=p*a[i,j];
end;
writeln(‘ *Результат*’);
write(‘ ***’, p,’***’);
end.
Пример7_12. Вычисление произведения двух матриц а (2,3) иb(3, 2)
Program Prog10;
Uses WinCrt;
var
a,b,c:array[1..5,1..5] of integer;
i,j,f,s:byte;
begin
writeln('Даны две матрицы');
randomize;
for i:=1 to 2 do
begin
for j:=1 to 3 do
a[i,j]:=random(10);
end;
for i:=1 to 2 do
begin
for j:=1 to 3 do
begin
write(a[i,J]:3);
end;
writeln;
end; {Заполение и вывод матриц}
writeln;
for j:=1 to 3 do
for f:=1 to 2 do
b[j,f]:=random(10);
for j:=1 to 3 do
begin
for f:=1 to 2 do
write(b[j,f]:3);
writeln;
end;
writeln;
writeln('3aдaние: найти произведение этих матриц');
writeln;
for i:=1 to 2 do
for f:=1 to 2 do
begin
s:=0;
for j:=1 to 3 do {поиск произведения}
s:=s+a[i,J]*b[j,f];
c[i,f]:=s;
end;
for i:=1 to 2 do
begin
for f:=1 to 2 do {вывод результата}
write(c[i,f]:5);
writeln;
end;
readln;
readln;
end.
Пример7_13. Получить единичную матрицу путем замены элементов на главной диагонали на 1, а остальные – на 0
Program mas4;
var
a:array[1..5,1..5] of integer;
i,j:byte;
begin
writeln (‘Дана матрица:5*5’);
for i:=1 to 5 do
for j:=1 to 5 do {заполнение и вывод массива}
a[i,j]:=random(100); {датчик случайных чисел}
for i:=1 to 5 do
begin
for j:=1 to 5 do
write(a[i,j]:3);
writeln;
end;
writeln;
writeln(‘Задание: получить единичную матрицу’);
writeln(‘путем замены элементов на главной’);
writeln(‘диагонали на1, а остальные – на 0’);
for i:=1 to 5 do
for j:=1 to 5 do
ifi=j then {замена элементов массива в соответствии}
{с определением единичной матрицы}
a[i,j]:=1
else
a[i,j]:=0;
writeln;
writeln(‘Результат’);
for i:=1 to 5 do
begin
for j:=1 to 5 do {вывод результата}
write(a[i,j]:3);
writeln;
end;
end.
Пример7_14. Поменять местами два элемента в двумерном массиве
Program mas5;
uses wincrt;
const
n=4;
type
t=array[1..n] of integer;
var
b:boolean;
a:array[1..n] of t;
i,j,f.e,g,s:byte;
k:integer;
begin
writeln(‘Дана матрица:’);
randomize;
for i:=1 to n do
begin
for j:=1 to n do
begin {заполнение и вывод массива}
a[i,j]:=random(20);
write(a[i,j]:3);
end;
writeln;
end;
writeln(‘Задание: поменять местами любые два элемента’);
repeat
writeln(‘введите номера строк’);
b:=false;
readln(f);
readln(e); {считывание номеров строк и столбцов}
writeln(‘введите номера столбцов’);
readln(g);
readln(s);
if (f<=n) and (e<=n) and (g<=n) and (s<=n) then
b:=true
else
writeln(‘Массив', n,'х',n, 'Введите числа<4.’);
writeln;
until b=true;
k:=a[e,s];
a[e,s]:=a[f,g]; {перестановка элементов}
a[f,g]:=k;
writeln(‘измененная матрица’);
for i:=1 to n do
begin
for j:=1 to n do
write(a[i,j]:3); { вывод результата }
writeln;
end;
end.
Пример7_15. В двумерном массиве найти сумму максимального и минимального элементов, если она меньше 0, тогда все отрицательные элементы матрицы, лежащие выше главной диагонали, заменить на нули.
prodram konst1;
var
a:array[1..6,1..6] of integer;
max, min,i,j,p:integer;
begin
writeln(‘В двумерном массиве найти сумму макс. и мин.
элемента,’);
writeln(‘если она меньше 0, тогда все отрицательные элементы
матрицы,’);
writeln(‘лежащие выше главной диагонали, заменить на нули.’);
writeln(‘Исходная матрица’);
for i:=1 to 6 do
for j:=1 to 6 do
read (a[i,j]); {считывание массива из файла}
for i:=1 to 6 do
begin
for j:=1 to 6 do
write(a[i,j]:3); {вывод массива в матричной форме}
writeln;
end;
writeln;
max:=a[1,1];
for i:=1 to 6 do
for j:=1 to 6 do {поиск и вывод максимального элемента}
if max<a[i,j] then max:=a[i,j];
writeln(‘максимальный элемент’,max);
min:=a[1,1];
for i:=1 to 6 do
for j:=1 to 6 do
if min>a[i,j] then min:=a[i,j]; {поиск и вывод
минимального элемента}
writeln(‘минимальный элемент’,min);
p:=min+max; {поиск и вывод суммы}
writeln(‘сумма макс. и мин. элемента’,p);
if p<0 then begin
for i:=1 to 6 do
for j:=1 to 6 do
if (i<j) and (a[i,j]<0) then a[i,j]:=0; {замена
элементов по условию}
end;
writeln(‘измененная матрица”);
for i:=1 to 6 do
begin
for j:=1 to 6 do {вывод измененного массива в
матричной форме}
write(a[i,j]:3);
writeln:
end;
readln;
end.
Пример7_16.Пусть надо посчитать общее количество продукции,е пускаемой каждым заводом, и количество продукции каждого наимено ния, выпускаемой всеми заводами.
Вычисляемые и исходные данные объединить в одну таблицу.
Изделие1 Изделие 2 изделие 3 Изделие 4 Всего
Завод 1 |
|
|
|
|
|
Завод 2 |
|
|
|
|
|
Завод 3 |
|
|
|
|
|
Всего |
|
|
|
|
|
Для представления таблицы в программе используем двумерный массив:
ргоd: аггау [1..zab+1,1..izd+].
Ниже приведен текст программы, решающей поставленную задачу.
cost:
zab=3 ;
izd=4;
var
prod:аггау[1..zab+1,1..izd+1] of integer;
i:integer; { номер завода }
j:integer; { номер изделия }
begin
writeln( 'Ввод исходных данных.' ) ;
for i:=1 to zav do
begin
writeln ('Завод', i:2);
for j:=1 to izd do
begin
write ('Изделие', j:2, ' ');
readln (prod[i,j]);
end;
end;
{вычислим общее колическтво изделий
выпускаемых каждым заводом}
for i:=1 to zav do
begin
prod [i,izd+1]:=0;
for j:=1 to izd do
prod[i,izd+1]:= prod [i,izd+1]+prod[i,j];
end;
{вычислим количество изделий одного наименованияб
выпущенных всеми заводами}
forj:=1toizddo
begin
prod [zav+1,j]:=0;
for i:=1 to zav do
prod [zav+1,j]:=prod[zav+1]+prod[i,j];
end;
{вывод итоговой таблицы}
writeln(' 1 2 3 4 Всего');
for i:=1 to zav+1 do
begin
if i< zav then write ('Завод ', i:2)
else write ('Всего ');
for j:=1 to izd +1 do
write (prod[i,j]:5;
writeln;
end;
end.
Пример работы программы:
Ввод исходных данных. Завод 1
Изделие 1->120
Изделие 2->100
Изделие 3->100
Изделие 4->25 Завод 2
Изделие 1->100
Изделие 2->50
Изделие 3->75
Изделие 4->40
Завод 3
Изделие 1->75
Изделие 2->50
Изделие 3->50
Изделие 4->50
1 2 3 4 Всего
Завод 1 120 100 100 25 345
Завод 2 100 50 75 40 265
Завод 3 75 50 50 50 225 <
Зсего 295 200 225 115 835
Обратите внимание на использование констант в программе. Если изменятся исходные данные, например, число заводов, то надо будет внести изменения только в разделе описания констант.
Следующая программа обрабатывает результаты соревнований по легкой атлетике.
Завоевано медалей:
Золотые Серебряные Бронзовые
Буревестник 4 4 4
Динамо 2 4 3
Зенит 6 4 4
Спартак 3 3 4
Программа считывает исходные данные, вводимые с клавиатуры, вычисляет общее количество медалей и затем расставляет клубы по порядку в соответ-
ствии с общим количеством медалей. Для представления данных о
количестве медалей используется двумерный массив medal, количество строк которого на единицу больше, чем количество клубов, а количество столбцов на единицу больше, чем видов медалей. Дополнительный столбец используется
для хранения общего количества медалей, которое вычисляется после ввода исходных данных, а дополнительная строка — как буфер при обмене строк во время сортировки строк таблицы.
{ Обработка результатов соревнований }
const
NC = 4; { число клубов- участников }
var
club:array[1..NC + 1] of string[30]; {клуб }
medal:array[1..NC+1,1..4] of integer; {количество медалей }
m:integer;
i,j:integer;
begin
club[1]:='Буревестник';
club[2]:='Динамо ';
club[3]:='Зенит ';
club[4]:='Спартак ';
writeln('Для каждой команды в одной строке введите через пробел');
writeln('число золотых, серебряных и бронзовых медалей');
writeln('и нажмите <Enter>' );
for i:=1 to NC do
begin
write (club[i], ' ');
readln (medal[i,1],medal[i,2],medal[i,3]);
end;
{ подсчет общего количества медалей}
for i:=1 to NC do
begin
medal[i,4]:=0;
for j:=1 to 3 do
medal[i,4]:= medal[i,4]+medal[i,j];
end;
{ сортировка таблицы }
for i:=1 to NC-1 do
begin
{ найти строку, в которой максимально общее число число
медалей}
m:=i;
for j:=i+1 to NC do
if medal[j,4]>medal[m,4] then m:=j;
{обменяем i- строку с m-й }
club[NC+1]:=club[i];
club[i]:=club[m];
club[m]:=club[NC+1];
for j:=1 to 4 do
begin
medal[NC+1,j]:=medal[i,j];
medal[i,j]:=medal[m,j];
medal[m,j]:=medal[NC+1,j];
end;
end;
{ вывод итоговой таблицы }
writeln;
writeln(' Клуб Золотые Серебряные Бронзовые Всего');
writeln('** Итоговая таблица **');
for i := 1 to NC do
begin
write(i:2,'. ',club[i]);
for j:=1 to 4 do
write(medal[i,j]:11);
writeln;
end;
end.
Пример работы программы:
Для каждой команды в одной строке введите через пробел
число золотых, серебряных и бронзовых медалей
и нажмите <Еnter> ;
Буревестник 4 4 4
Динамо 2 4 3
Зенит 6 4 4
Спартак 3 3 4
** Итоговая таблица **
Клуб Золотые Серебряные Бронзовые Всего
1. Зенит 6 4 4 14
2. Буревестник 4 4 4 12
3.Спартак 3 3 4 10
4. Динамо 2 4 3 9
МНОЖЕСТВА