Архитектура Аудит Военная наука Иностранные языки Медицина Металлургия Метрология Образование Политология Производство Психология Стандартизация Технологии |
Модульная структура программного изделия
Программное изделие должно быть отдельным модулем, файл LAВ2.C, в котором должны размещаться как данные (матрица и вспомогательная информация), так и функции, которые обеспечивают доступ. Внешний доступ к программам и данным модуля возможен только через вызов функций чтения и записи элементов матрицы. Доступные извне элементы программного модуля должны быть описаны в отдельном файле LAВ2.H, который может включаться в программу пользователя оператором препроцессора: #include "lab2.h" Пользователю должен поставляться результат компиляции - файл lAВ2.0ВJ и файл lAВ2.H. Преобразование 2-компонентного адреса элемента матрицы, которую задает пользователь, в l-компонентную должно выполняться отдельной функцией (так называемой, функцией линеаризации), вызов которой возможен только из функций модуля. Возможны три метода преобразования адреса: - при создании матрицы для нее создается также и дескриптор D[N] - отдельный массив, каждый элемент которого соответствует одной строке матрицы; дескриптор заполняется значениями, подобранными так, чтобы: n = D[x] + у, где х, у - координаты пользователя (строка, столбец), n - линейная координата; - линейная координата подсчитывается методом итерации как сумма полезных длин всех строк, предшествующих строке х, и к ней прибавляется смещение у-го полезного элемента относительно начала строки; - для преобразования подбирается единое арифметическое выражение, которой реализует функцию: n = f (х,у). Первый вариант обеспечивает быстрейший доступ к элементу матрицы, ибо требует наименьших расчетов при каждом доступе, но плата за это - дополнительные затраты памяти на дескриптор. Второй вариант - наихудший по всем показателям, ибо каждый доступ требует выполнения оператора цикла, а это и медленно, и занимает память. Третий вариант может быть компромиссом, он не требует дополнительной памяти и работает быстрее, чем второй. Но выражение для линеаризации тут будет сложнее, чем первом варианте, следовательно, и вычисляться будет медленнее. В программном примере, который мы приводим ниже, полностью реализован именно третий вариант, но далее мы показываем и существенные фрагменты программного кода для реализации и двух других. Описание логической структуры Общие переменные В файле LАВ2.С описаны такие статические переменные: - int NN - размерность матрицы; - int SIZE - количество ненулевых элементов в матрице; - int *m_addr - адрес сжатой матрицы в памяти, начальное значение этой переменной - NULL - признак того, что память не выделена; - int L2_RESULT - общий флаг ошибки, если после выполнения любой функции он равен -1, то произошла ошибка. Переменные SIZE и m_addr описаны вне функций с квалификатором static, это означает, что вони доступны для всех функций в этом модуле, но недоступны для внешних модулей. Переменная L2_RESULT также описана вне всех функций, не без явного квалификатора. эта переменная доступна не только для этого модуля, но и для всех внешних модулей, если она в них буде описана с квалификатором extern. Такоеописание имеется в файле LAВ2.H. Функция crea t _matr Функция creat_matr предназначена для выделения в динамической памяти места для размещения сжатой матрицы. Прототип функции: int creaCmat r ( int N ); где N - размерность матрицы. Функция сохраняет значение параметра в собственной статической переменной и подсчитывает необходимый размер памяти для размещения ненулевых элементов матрицы. Для выделения памяти используется библиотечная функция С mallos. Функция возвращает -1, если при выделении произошла ошибка, или 0, если выделение прошло нормально. При этом переменной L2_RESULT также присваивается значение 0 или -1. Функция close_matr Функция close_matr предназначена для освобождения памяти при завершении работы с матрицей. Прототип функции: int close _ mat г ( void ); Функция возвращает 0 при успешном освобождении, -1 - при попытке освободить невыделенную память. Если адрес матрицы в памяти имеет значения NULL, это признак того, что память не выделялась, тогда функция возвращает -1, иначе - освобождает память при помощи библиотечной функции free и записывает адрес матрицы - NULL. Соответственно функция также устанавливает глобальный признак ошибки- L2_RE8ULT. Функция read_matr Функция read_matr предназначена для чтения элемента матрицы. Прототип функции: int г ead _ mat г( int х, int y ); где х и у – координаты (строка и столбец). Функция возвращает значение соответствующего элемента матрицы. Если после выполнения функции значение переменной L2_RE8ULT -1, то это указывает на ошибку при обращении. Проверка корректности задания координат выполняется обращением к функции ch_coord, если эта последняя возвращает ненулевое значение, выполнение read_matr на этом и заканчивается. Если же координаты заданы верно, то проверяется попадание заданногo элемента в нулевой или ненулевой участок. Элемент находится в нулевом участке, если для него номер строки больше, чем номер столбца. Если элемент в нулевом участке, функция просто возвращает 0, иначе - вызывает функцию линеаризации lin и использует значение, которое возвращает lin, как индекс в массиве m_addr, по которому и выбирает то значения, которое возвращается. Функция write_matr Функция write_matr предназначена для записи элемента в матрицу. Прототип функции: int w г ite _ mat г( int х, int y , int value ); где х и у - координаты (строка и столбец), value - то значение, которое нужно записать. Функция возвращает значение параметра va l ue, или 0 - если была попытка записи в нулевой участок. Если после выполнения функции значение переменной L2_RE8ULT -1, то это указывает на ошибку при обращении. Выполнение функции подобно функции read_matr с тем отличием, что, если координаты указывают на ненулевой участок, то функция записывает value в массив m_addr. Функция ch_coord Функция ch_coord предназначена для проверки корректности задания координат. Эта функция описана как static и поэтому может вызываться только из этого же модуля. Прототип функции: static charch _ coord ( int х, int у); где х и у - координаты (строка и столбец). Функция возвращает о, если координаты верные, -1 - если неверные. Соответственно, функция также устанавливает значение глобальной переменной L2_RESULT. Выполнение функции собственно состоит из проверки трех условий: - адрес матрицы не должен быть NULL, то есть, матрица должна уже находиться в памяти; - ни одна из координат не может быть меньше 0; - ни одна из координат не может быть больше NN. Если хотя бы одно из этих условий не выполняется, функция устанавливает признак ошибки. Функция lin Функция lin предназначена для преобразования двумерных координат в индекс в одномерном массиве. Эта функция описана как static и поэтому может вызываться только из этого же модуля. Прототип функции: static int lin ( int х, int у); где х и у - координаты (строка и столбец). Функция возвращает координату в массиве m_addr. Выражение, значение которого вычисляет и возвращает функция, подобрано вот из каких соображений. Пусть мы имеет такую матрицу, как показано ниже, и нам нужно найти линейную координату элемента, обозначенного буквой А с координатами (х,у): Координату элемента можно определить как: n = SIZE - sizeX + offY , где SIZE - общее количество элементов в матрице, SIZE = NN * ( NN - 1) / 2 + NN ; sizeX - количество ненулевых элементов, которые содержатся в строке х и ниже, sizeX = (NN - х) * (NN - х - 1) / 2 + (NN - х); of f Y - смещение нужного элемента от начала строки х, offY = у – х Программа пользователя Для проверки функционирования нашего модуля создается программный модуль, который имитирует программу пользователя. Этот модуль обращается к функции creat_matr для создания матрицы нужного размера, заполняет ненулевую ее часть последовательно увеличивающимися числами, используя для этого функцию write_matr, и выводит матрицу на экран, используя для выборки ее элементов функцию read_matr. Далее в диалоговом режиме программа вводит запрос на свои действия и читает/пишет элементы матрицы с заданными координатами, обращаясь к функциям read_matr/ write_matr. Если пользователь захотел закончить работу, программа вызывает функцию close_matr. |
Последнее изменение этой страницы: 2019-05-08; Просмотров: 206; Нарушение авторского права страницы