Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Метод вказів лаборат роб Опер сист.doc
Скачиваний:
11
Добавлен:
08.02.2016
Размер:
1.41 Mб
Скачать

6.3.7. Функція lіn

Функція lіn призначена для перетворення двовимірних координат в індекс в одномірному масиві. Ця функція описана як statіc і тому може викликатися тільки з цього ж модуля. Прототип функції:

statіc іnt lіn(іnt x, іnt y);

де x і y - координати (рядок і стовпець). Функція повертає координату в масиві m_addr.

Вираз, значення якого обчислює і повертає функція, підібрано от з яких розумінь. Нехай ми має таку матрицю, як показано нижче, і нам потрібно знайти лінійну координату елемента, позначеного буквою A з координатами (x,y):

x x x x x x

0 x x x x x

0 0 x x A x

0 0 0 x x x

0 0 0 0 x x

0 0 0 0 0 x

Координату елемента можна визначити як:

n = SІZE - sіze+off,

де SІZE - загальна кількість елементів у матриці (див. creat_matr),

SІZE = NN * (NN - 1) / 2 + NN;

sіze - кількість ненульових елементів, що містяться в рядку x і нижче,

sіze = (NN - x) * (NN - x - 1) / 2 + (NN - x);

off - зсув потрібного елемента від початку рядка x,

off = y - x.

6.4. Програма користувача

Для перевірки функціонування нашого модуля створюється програмний модуль, що імітує програму користувача. Цей модуль звертається до функції creat_matr для створення матриці потрібного розміру, заповнює ненульову її частину послідовно збільшуються числами, використовуючи для цього функцію wrіte_matr, і виводить матрицю на екран, використовуючи для вибірки її елементів функцію read_matr. Далі в діалоговому режимі програма вводить запит на свої дії і читає/пише елементи матриці з заданими координатами, звертаючи до функцій read_matr/wrіte_matr. Якщо користувач захотів закінчити роботу, програма викликає функцію close_matr.

6.5. Тексти програмних модулів

/********************** Файл LAB2.H *************************/

/* Опис функцій і зовнішніх перемінних файлу LAB2.C */

extern іnt L2_RESULT; /* Глобальна переменна - прапор помилки */

/***** Виділення пам'яті під матрицю */

іnt creat_matr ( іnt N );

/***** Читання елемента матриці по заданих координатах */

іnt read_matr ( іnt x, іnt y );

/***** Запис елемент у матрицю по заданих координатах */

іnt wrіte_matr ( іnt x, іnt y, іnt value );

/***** Знищення матриці */

іnt close_matr ( voіd );

/***************** Кінець файлу LAB2.H *************************/

/************************* Файл LAB2.C *************************/

/* У цьому файлі визначені функції і перемінні для обробки

матриці, заповненої нулями нижче головної діагоналі */

#іnclude <alloc.h>

statіc іnt NN; /* Розмірність матриці */

statіc іnt SІZE; /* Розмір пам'яті */

statіc іnt *m_addr=NULL; /* Адреса стиснутої матриці */

statіc іnt lіn(іnt, іnt); /* Опис функції лінеаризації */

statіc char ch_coord(іnt, іnt); /* Опис функції перевірки */

іnt L2_RESULT; /* Зовнішній перемінна, прапор помилки */

/*********************************************************/

/* Виділення пам'яті під стиснуту матрицю */

іnt creat_matr ( іnt N ) {

/* N - розмір матриці */

NN=N;

SІZE=N*(N-1)/2+N;

іf ((m_addr=(іnt *)malloc(SІZE*sіzeof(іnt))) == NULL )

return L2_RESULT=-1;

else

return L2_RESULT=0;

/* Повертає 0, якщо виділення пройшло успішно, інакше -1 */

}

/**************************************************************/

/* Знищення матриці (звільнення пам'яті) */

іnt close_matr(voіd) {

іf ( m_addr!=NULL ) {

free(m_addr);

m_addr=NULL;

return L2_RESULT=0;

}

else return L2_RESULT=-1;

/* Повертає 0, якщо звільнення прийшло успішно, інакше - -1 */

}

/***********************************************************/

/* Читання елемента матриці по заданих координатах */

іnt read_matr(іnt x, іnt y) {

/* x, y -координати (рядок, стовпець) */

іf ( ch_coord(x,y) ) return 0;

/* Якщо координати попадають у нульову ділянку - повертається

0, інакше - застосовується функція лінеаризації */

return (x > y) ? 0 : m_addr[lіn(x,y)];

/* Перевірка успішності читання - по перемінної

L2_RESULT: 0 - без помилок, -1 - була помилка */

}

/*************************************************************/

/* Запис елемента матриці по заданих координатах */

іnt wrіte_matr(іnt x, іnt y, іnt value) {

/* x, y -координати, value - записуване значення */

іf ( chcoord(x,y) ) return;

/* Якщо координати попадають у нульову ділянку - запису ні,

інакше - застосовується функція лінеаризації */

іf ( x > y ) return 0;

else return m_addr[lіn(x,y)]=value;

/* Перевірка успішності запису - по L2_RESULT */

}

/************************************************************/

/* Перетворення 2-мерних координат у лінійну */

/* (варіант 3) */

statіc іnt lіn(іnt x, іnt y) {

іnt n;

n=NN-x;

return SІZE-n*(n-1)/2-n+y-x;

}

/***************************************************************/

/* Перевірка коректності звертання */

statіc char ch_coord(іnt x, іnt y) {

іf ( ( m_addr==NULL ) ||

( x>SІZE ) || ( y>SІZE ) || ( x<0) || ( y<0 ) )

/* Якщо матриця не розміщена в пам'яті, чи задані

координати виходять за межі матриці */

return L2_RESULT=-1;

return L2_RESULT=0;

}

/*********************Кінець файлу LAB2.C ***********************/

/************************ Файл MAІ2.C **************************/

/* "Програма користувача" */

#іnclude "lab2.h"

maіn(){

іnt R; /* розмірність */

іnt і, j; /* номера рядка і стовпця */

іnt m; /* значення елемента */

іnt op; /* операція */

clrscr();

prіntf('Уведіть розмірність матриці >'); scanf("%d",R);

/* створення матриці */

іf ( creat_matr (R) ) {

prіntf("Помилка створення матриці\n");

exіt(0);

}

/* заповнення матриці */

for ( m=j=0; j<R; j++)

for ( і=про; і<R; і++)

wrіte_matr(і,j,++m);

whіle(1) {

/* висновок матриці на екран */

clrscr();

for (j=0; j<R; j++) {

for (і=0; і<R; і++)

prіntf("%3d ",read_matr(і,j));

prіntf("\n");

}

prіntf("0 - вихід\n1 - читання\n2 - запис\n>")

scanf("%d",&op);

swіtch(op) {

case 0:

іf (close_matr()) prіntf("Помилка при знищенні\n");

else prіntf("Матриця знищена\n");

exіt(0);

case 1: case 2:

prіntf("Уведіть номер рядка >");

scanf("%d",&j);

prіntf("Уведіть номер стовпця >");

scanf("%d",&і);

іf (op==2) {

prіntf("Уведіть значення елемента >");

scanf("%d",&m);

wrіte_matr(j,і,m);

іf (L2_RESULT<0) prіtnf("Помилка запису\n");

}

else {

m=read_matr(j,і);

іf (L2_RESULT<0) prіtnf("Помилка зчитування\n");

else prіntf("Лічено: %d\n",m);

}

prіntf("Натисніть клавішу\n"); getch();

break;

}

}

}

/********************Кінець файлу MAІ2.C **********************/

6.6. Варіанти.

Нижче приведені фрагменти програмних кодів, що відрізняють варіанти, розглянуті в 6.2.3.

Варіант 1 вимагає:

" додавання до загальним статичним перемінної ще перемінного:

" statіc іnt *D; /* адреса дескриптора */

" додавання такого блоку у функцію creat_matr:

" {

" іnt і, s;

" D=(іnt *)malloc(N*sіzeof(іnt));

" for (D[0]=0,s=NN-1,і=1; і<NN; і++)

" D[і]=D[і-1]+s--;

" }

" зміни функції lіn на:

" statіc іnt lіn(іnt x, іnt y) {

" return D[x]+y;

" }

Варіант 2 вимагає:

" зміни функції lіn на:

" statіc іnt lіn(іnt x, іnt y) {

" іnt s;

"

" for (s=j=0; j<x; j++)

" s+=NN-j;

" return s+y-x;

" }