Задача «Формирование массива и изменение массива»

Постановка задачи. Даны три прямоугольные матрицы a, b и c разного размера. Сформировать массивы из чётных элементов верхней половины матрицы a, нижней половины матрицы b, левой половины матрицы c. Из первого полученного одномерного массива удалить элементы, равные минимальному элементу второго массива и равные минимальному элементу третьего массива. В случае нечётного количества строк и/или столбцов одной или нескольких матриц выводить соответствующие сообщения и обрабатывать меньшую часть матрицы (матриц). Для обработки матриц использовать процедуру – одну (!) для всех матриц. Результатом этой процедуры должен быть одномерный массив, а также количество элементов этого массива. Для удаления элементов из массива также использовать процедуру. При удалении элементы, расположенные после удаляемого, следует сдвигать к началу массива. Для поиска значения, используемого при удалении элементов из массива, использовать функцию, вызов которой должен быть фактическим параметром процедуры удаления элементов. Для ввода матриц и вывода массивов также использовать процедуры. Ввод всех данных осуществляется из файла, вывод – в файл. Для передачи имён файлов должны использоваться параметры программы.

Шаг 1. Общая структура программы

Программа на процедурном языке программирования состоит из данных и действий по их обработке. program ArrayForm; { Описание данных – констант, типов и переменных } begin { Обработка данных } end.

Шаг 2. Разработка структуры данных

Из постановки задачи следует, что на вход программы подаётся три матрицы a, b и c. Также должны быть заданы их размеры ma, na, mb, nb и mc, nc.

Из постановки задачи также следует, что надо сформировать три массива d, e и f, а также определить их размеры nd, ne и nf. Затем из массива d необходимо удалить элементы, равные минимальному элементу массива e и равные минимальному элементу массива f. Результатом работы программы будут массивы d, e и f и их размеры nd, ne и nf, при этом массив d будет не только сформирован, но и изменён.

Для задания массивов и матриц введём константу, ограничивающую максимально возможное количество строк и столбцов матрицы, и типы для массивов и матриц. program ArrayForm; const nmax = 10; type matrix = array [1..nmax, 1..nmax] of integer; mas = array [1..nmax * nmax div 2] of integer; var { Входные данные } a, b, c: matrix; { Исходные матрицы } ma, na, mb, nb, mc, nc: integer; { Количество строк и столбцов матриц a, b, c соответственно } { Выходные данные } d, e, f: mas; { Формируемые массивы } nd, ne, nf: integer; { Количество элементов массивов d, e, f соответственно } begin { Обработка данных } end.

Шаг 3. Разработка тестов

№ теста Входные данные Ожидаемые результаты Смысл теста
1 ma = 4, na = 4
a:  1   2   3   4
    5   6   7   8
    9  10  11  12
   13  14  15  16
mb = 4, nb = 6
b:  5   2   7  42   3   0
   35   6   8  10  12  17
   78  11  19  62  -7  41
   33  18  50   6  22  40
mc = 4, nc = 4
c:  1  11  77  51
    9   5  13  85
   93  17  41  71
   15  -1  -5  55
nd = 4, 3
d: {2, 4, 6, 8}, {2, 4, 8}
ne = 7
e: {78, 62, 18, 50, 6, 22, 0}
nf = 0
f: { }
Получаем массивы по правилу, указанному в постановке задачи. Полученные массивы имеют разное количество элементов. Из первого массива удаляем средний элемент. Поскольку третий массив пустой, удаление минимального элемента третьего массива не выполняется.
2 ma = 5, na = 3
a:  1   2   3
    4   5  10
    7   8   9
   10  11  12
   13  14  15
mb = 5, nb = 3
b:  1   2   3
    4   5   6
    7   8   9
   10  11  12
   13  16  15
mc = 3, nc = 5
c:  5   6  -8   1   3
   92   5  15  -4   7
   2  25   1  12  18
nd = 3, 1
d: {2, 4, 10}, {4}
ne = 3
e: {10, 12, 16}
nf = 4
f: {6, 92, 2}
Получаем массивы по правилу, указанному в постановке задачи. Полученные массивы имеют разное количество элементов. Из первого массива удаляем первый и последний элементы.
3 ma = 4, na = 3
a:  1   2   3
    4   5   6
    7   8   9
   10  11  12
mb = 3, nb = 3
b:  7   8   9
    4   5   6
    1   2   3
mc = 4, nc = 4
c:  5   6   8   1
    9  51  15  -4
    4  11   1  12
   21   3   9  18
nd = 3, 0
d: {2, 4, 6}, {}
ne = 1
e: {2}
nf = 2
f: {6, 4}
Получаем массивы по правилу, указанному в постановке задачи. Полученные массивы имеют разное количество элементов. Из первого массива удаляем все элементы.
4 ma = 3, na = 3
a:  5   7   9
   11  13  19
    7   8   9
   25  35  55
mb = 3, nb = 3
b:  1   2   3
    4   5   6
    7   8   9
mc = 3, nc = 4
c: -1   -2   -3   -4
   -5   -6   -7   -8
   -9  -10  -11  -12
nd = 0
d: {}
ne = 1
e: {8}
nf = 3
f: {-2, -6, -10}
Получаем массивы по правилу, указанному в постановке задачи. Полученные массивы имеют разное количество элементов. Первый массив пустой, удаление не производится.
5 ma = 3, na = 3
a:  8   8   8
    8   8   8
    8   8   8
mb = 5, nb = 3
b:  1   5   8
   -3  -6   9
   11  12  40
   25  13  33
   10   8  15
mc = 3, nc = 5
c:  1   2   3   4   5
    6   7   8   9  10
   11  12  13  14  15
nd = 3, 0
d: {8, 8, 8}, {}
ne = 2
e: {10, 8}
nf = 3
f: {2, 6, 12}
Получаем массивы по правилу, указанному в постановке задачи. Полученные массивы имеют разное количество элементов. В первом массиве все элементы одинаковы, все они удаляются.

Шаг 4. Разработка общей структуры программы

Программа должна состять из трёх основных частей – ввод исходных данных, получение результатов, вывод полученных результатов. program ArrayForm; const nmax = 10; type matrix = array [1..nmax, 1..nmax] of integer; mas = array [1..nmax * nmax div 2] of integer; var { Входные данные } a, b, c: matrix; { Исходные матрицы } ma, na, mb, nb, mc, nc: integer; { Количество строк и столбцов матриц a, b, c соответственно } { Выходные данные } d, e, f: mas; { Формируемые массивы } nd, ne, nf: integer; { Количество элементов массивов d, e, f соответственно } begin { Ввод исходных данных } { Формирование массивов } { Вывод результатов } end.

Шаг 5. Разработка ввода и вывода

Организуем ввод из файла и вывод в файл с использованием параметров программы, проверкой правильности передачи параметров и существования входного файла, как уже было сделано в лабораторной работе № 6. Для ввода и вывода массивов будем использовать процедуры.

В качестве заглушки для обработки данных сформируем пока пустые массивы.

Входная форма

Выходная форма

program ArrayForm; const nmax = 10; type matrix = array [1..nmax, 1..nmax] of integer; mas = array [1..nmax * nmax div 2] of integer; var { Входные данные } a, b, c: matrix; { Исходные матрицы } ma, na, mb, nb, mc, nc: integer; { Количество строк и столбцов матриц a, b, c соответственно } { Выходные данные } d, e, f: mas; { Формируемые массивы } nd, ne, nf: integer; { Количество элементов массивов d, e, f соответственно } { Промежуточные данные } fin, fout: TextFile; { Файловые переменные } { Процедура ввода матрицы из файла } procedure Get(var x: matrix; var m, n: integer; var f: TextFile); ... { Процедура вывода матрицы в файл } procedure Put(const x: matrix; m, n: integer; name: string; var f: TextFile); ... { Процедура вывода одномерного массива в файл } procedure Put(const x: mas; n: integer; name: string; var f: TextFile); ... begin if ParamCount < 2 then { Проверяем количество параметров } writeln('Недостаточно параметров!') else begin if not FileExists(ParamStr(1)) then { Проверяем существование файла } writeln('Невозможно открыть файл ''', ParamStr(1), ''' для чтения') else begin { Ввод исходных данных } AssignFile(fin, ParamStr(1)); { Открываем файл } Reset(fin); Get(a, ma, na, fin); Get(b, mb, nb, fin); Get(c, mc, nc, fin); CloseFile(fin); { Закрываем файл } { Формирование массивов – заглушка } nd := 0; ne := 0; nf := 0; { Вывод результатов } AssignFile(fout, ParamStr(2)); Rewrite(fout); Put(a, ma, na, 'A', fout); Put(b, mb, nb, 'B', fout); Put(c, mc, nc, 'C', fout); if ma mod 2 = 1 then writeln(fout, 'Матрица A содержит нечётное количество строк. Обрабатываем ', ma div 2, ' из них.'); Put(d, nd, 'D (верхняя половина матрицы A)', fout); if mb mod 2 = 1 then writeln(fout, 'Матрица B содержит нечётное количество строк. Обрабатываем ', mb div 2, ' из них.'); Put(e, ne, 'E (нижняя половина матрицы B)', fout); if mc mod 2 = 1 then writeln(fout, 'Матрица C содержит нечётное количество столбцов. Обрабатываем ', nc div 2, ' из них.'); Put(f, nf, 'F (левая половина матрицы C)', fout); CloseFile(fout); end; end; end.

Шаг 6. Разработка вычислительной части программы

Для решения задачи нам потребуется процедура EvenElements для формирования массива из чётных элементов части матрицы, функция Min для нахождения минимального элемента массива и процедура Delete для удаления из массива элементов, равных заданному числу. Процедура удаления элементов в качестве заданного числа будет получать результат вызова функции нахождения минимального элемента:
Delete(d, nd, Min(e, ne)); Delete(d, nd, Min(f, nf));

Шаг 7. Разработка интерфейса процедуры EvenElements

Процедура, как и любой алгоритм, должна получать данные и содержать действия по их обработке. В качестве исходных данных процедура должна получить матрицу, и, чтобы процедура могла обрабатывать любую часть матрицы, необходимо указать начальные и конечные значения для строк и столбцов. Выходными данными будут сформированный массив и количество его элементов. Входные и выходные данные процедуры передаются через параметры, при этом входную матрицу можно передать как параметр-константу, начальные и конечные значения – как параметры-значения, а выходные данные должны быть объявлены как параметры-переменные.

{ Процедура формирования массива из чётных элементов половины матрцы } procedure EvenElements(const x: matrix; ms, me, ns, ne: integer; var у: mas; var k: integer); var { Объявления локальных переменных } begin { Операторы } end;

Шаг 7. Тестирование интерфейса процедуры EvenElements

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

program ArrayForm; const nmax = 10; type matrix = array [1..nmax, 1..nmax] of integer; mas = array [1..nmax * nmax div 2] of integer; var { Входные данные } a, b, c: matrix; { Исходные матрицы } ma, na, mb, nb, mc, nc: integer; { Количество строк и столбцов матриц a, b, c соответственно } { Выходные данные } d, e, f: mas; { Формируемые массивы } nd, ne, nf: integer; { Количество элементов массивов d, e, f соответственно } { Промежуточные данные } fin, fout: TextFile; { Файловые переменные } { Процедура ввода матрицы из файла } procedure Get(var x: matrix; var m, n: integer; var f: TextFile); ... { Процедура вывода матрицы в файл } procedure Put(const x: matrix; m, n: integer; name: string; var f: TextFile); ... { Процедура вывода одномерного массива в файл } procedure Put(const x: mas; n: integer; name: string; var f: TextFile); ... { Процедура формирования массива из чётных элементов половины матрцы } procedure EvenElements(const x: matrix; ms, me, ns, ne: integer; var у: mas; var k: integer); var { Объявления локальных переменных } begin { Заглушка } k := 0; end; begin if ParamCount < 2 then { Проверяем количество параметров } writeln('Недостаточно параметров!') else begin if not FileExists(ParamStr(1)) then { Проверяем существование файла } writeln('Невозможно открыть файл ''', ParamStr(1), ''' для чтения') else begin { Ввод исходных данных } AssignFile(fin, ParamStr(1)); { Открываем файл } Reset(fin); Get(a, ma, na, fin); Get(b, mb, nb, fin); Get(c, mc, nc, fin); CloseFile(fin); { Закрываем файл } { Формирование массивов } EvenElements(a, 1, ma div 2, 1, na, d, nd); EvenElements(b, mb div 2 + 1 + mb mod 2, mb, 1, nb, e, ne); EvenElements(c, 1, mc, 1, nc div 2, f, nf); { Вывод результатов } AssignFile(fout, ParamStr(2)); Rewrite(fout); Put(a, ma, na, 'A', fout); Put(b, mb, nb, 'B', fout); Put(c, mc, nc, 'C', fout); if ma mod 2 = 1 then writeln(fout, 'Матрица A содержит нечётное количество строк. Обрабатываем ', ma div 2, ' из них.'); Put(d, nd, 'D (верхняя половина матрицы A)', fout); if mb mod 2 = 1 then writeln(fout, 'Матрица B содержит нечётное количество строк. Обрабатываем ', mb div 2, ' из них.'); Put(e, ne, 'E (нижняя половина матрицы B)', fout); if mc mod 2 = 1 then writeln(fout, 'Матрица C содержит нечётное количество столбцов. Обрабатываем ', nc div 2, ' из них.'); Put(f, nf, 'F (левая половина матрицы C)', fout); CloseFile(fout); end; end; end.

Шаг 8. Разработка процедуры EvenElements

Для формирования массива просматриваем в двух циклах указанную часть матрицы и добавляем чётные элементы в формируемый массив.

{ Процедура формирования массива из чётных элементов половины матрцы } procedure EvenElements(const x: matrix; ms, me, ns, ne: integer; var у: mas; var k: integer); begin k := 0; for i: integer := ms to me do for j: integer := ns to ne do if x[i, j] mod 2 = 0 then begin k := k + 1; y[k] := x[i, j]; end; end;

Далее аналогично разрабатываем две оставшиеся подпрограммы. Желательно сначала проверить правильность работы функции поиска минимального элемента, выводя результаты её работы, затем можно будет использовать её для передачи параметра в процедуру удаления элементов. Добавляем в программу вызовы процедуры удаления элементов и вывод изменённого массива d.