Загальна структура MPI програми. Отримання інформації про розмір комунікатора, ранг процесу.

Загальна структура MPI програми. Отримання інформації про розмір комунікатора, ранг процесу.

Найбiльш загальним пiдходом при створеннi паралельних програм в даний час є застосу- вання бiблiотеки передачi повiдомлень, де процеси використовують звернення до бiблiотеки MPI (Message Passing Interface), щоб обмiнюватися повiдомленнями (iнформацiєю) з iншими процесами. Механiзм передачi повiдомлень дозволяє процесам, запущеним на ба- гатопроцесорнiй системi, спiльно вирiшувати великi завдання. Iснує декiлька функцiй, якi використовуються в будь-якому, навiть самому короткому додатку MPI. Займаються вони не стiльки власне передачею даних, скiльки її забезпеченням:

Iнiцiалiзацiя бiблiотеки.MPI_Init( &argc, &argv );

Аварiйне закриття бiблiотеки. Викликається, якщо програма користувача завершує- ться через помилку часу виконання, пов’язаних з MPI:MPI_Abort();

Нормальне закриття бiблiотеки:MPI_Finalize();

Двi iнформацiйнi функцiї: повiдомляють розмiр групи (тобто загальну кiлькiсть зав- дань, пiд’єднаних до її областi зв’язку) i порядковий номер завдання: int size , rank;

MPI_Comm_size( MPI_COMM_WORLD, &size );

MPI_Comm_rank( MPI_COMM_WORLD, &rank );

Типи даних MPI. Створення і використання структур в MPI.

Для зменшення кiлькостi актiв обмiну та зручностi користувач може реєструвати в MPI свої власнi типи даних, наприклад, структури, пiсля чого MPI зможе обробляти їх нарiвнi з базовими. Загальнi правила:

• описи типiв створюються на базi створених ранiше користувацьких описiв, та на базi вбудованих описiв;

• вбудованi описи є для ВСIХ стандартних типiв Сi: MPI_INT, MPI_CHAR, MPI_FLOAT i так далi; тип

MPI_BYTE служить для передачi двiйкових даних Табл: 7.1;

• пiсля конструювання, але перед використанням опис повинен бути зареєстрований функцiєю MPI_Type_commit;

• використанi описи повиннi бути очищенi функцiєю MPI_Type_free.

MPI_Type_struct: створює опис структури

Прийом невідомих типів даних в MPI..

два джокера: MPI_ANY_SOURCE для номера зав- дання - вiдправника ("приймай вiд кого завгодно") та MPI_ANY_TAG для iдентифiкатора одержуваного повiдомлення ("приймай що завгодно"). MPI резервує для них якiсь негатив- нi цiлi числа, у той час як реальнi iдентифiкатори завдань i повiдомлень лежать завжди в дiапазонi вiд 0 до 32767. Користуватися джокерами слiд з обережнiстю, тому що помилково таким викликом MPI_Recv може захопити повiдомлення, яке повинно прийматися в iншiй частинi завдання-одержувача. Якщо логiка програми досить складна, використовувати джокери можна ТIЛЬКИ у 4 функцiях MPI_Probe i MPI_Iprobe, щоб перед фактичним прийомом дiзнатися тип i кiль- кiсть даних в повiдомленнi (взагалi-то, можна приймати, i не знаючи кiлькостi – був би приймальний буфер досить мiстким, але тип для MPI_Recv треба вказувати явно – а вiн може бути рiзним у повiдомленнях з рiзними iдентифiкаторами). Перевага джокерiв:

повiдомлення, що надходять витягуються по мiрi надходження, а не в мiру виклику MPI_Recv з потрiбними iдентифiкаторами завдань/повiдомлень. Це економить пам’ять i збiльшує швидкiсть роботи.

Декатрова топологія в MPI.

Топологiя – це механiзм спiвставлення процесам деякого комунiкатора альтернативної схеми адресацiї. В МРI топологiї вiртуальнi, тобто вони не пов’язанi з фiзичною топологiєю комунiкацiйної мережi. Топологiя використовується програмiстом для бiльш зручного по- значення процесiв, i таким чином, наближення паралельної програми до структури матема- тичного алгоритму. Крiм того, топологiя може використовуватися системою для оптимiзацiї розподiлу процесiв за фiзичними процесорами використовуваного паралельного комп’ютера за допомогою змiни порядку нумерацiї процесiв усерединi комунiкатора.

В МРI передбачено два типи топологiй:

• декартова топологiя (прямокутна решiтка довiльної розмiрностi);

• топологiя графа.

int MPI_Topo_test(MPI_Comm comm, int status); Функцiя визначення типу топологiї, пов’язаної з комунiкатором comm.

int MPI_Cart_create(MPI_Comm comm_old, int ndims, const int dims[], const int periods [], int reorder, MPI_Comm comm_cart); Створення комунiкатора comm_cart, що володiє декартовою топологiєю, з процесiв ко- мунiкатора comm_old

int MPI_Cart_coords(MPI_Comm comm, int rank, int maxdims, int coords[]); - Визначення декартових координат процеса по його рану rank в комунiкаторi comm. Вiдрахунок координат в кожному вимiрi починається з нуля.

int MPI_Cart_rank(MPI_Comm comm, const int coords[], int rank); - Визначення рангу процеса rank за його декартовими координатами coords.

int MPI_Cart_get(MPI_Comm comm, int maxdims, int dims[], int periods[], int coords[]); -Одержання iнформацiї про декартову топологiю котра пов’язана з комунiкатором comm та координат в нiй прцесу, що виклика дану функцiю. maxdims – задає розмiрнiсть топо- логiї. dims – повертає кiлькiсть процесiв для кожого вимiру. periods – перiодичнiсть по кожному вимiру. coords – координати процесу в декартовiй топологiї.

int MPI_Cart_shift(MPI_Comm comm, int direction, int disp, int rank_source, int rank_dest); Отримання номерiв посилаючого rank_source i приймаючого rank_dest процесiв в де- картовiй топологiї комунiкатора comm для здiйснення зсуву уздовж вимiру direction на величину disp.

Топологія графа в MPI.

int MPI_Graph_create(MPI_Comm comm_old, int nnodes, const int index[], const int edges[], int reorder, MPI_Comm comm_graph);

Створення, на основi комунiкатора comm_old, комунiкатора comm_graph з топологiєю графа. Параметер nnodes задає кiлькiсть вершин графа, index – задає сумарну кiлькiсть сусiдiв для перших вершин. Масив edges мiстить впорядкований список процесiв сусiдiв для всiх вершин. reorder – логiчний параметр, що визначає, чи системi дозволено мiняти порядок нумерацiї процесiв для оптимiзацiї розподiлу процесiв за фiзичними процесорам використовуваного паралельного комп’ютера.Фкнуцiя MPI_Graph_create є колективною, отже повинна бути викликана з кожного ппроцесу комунiкатора comm. Якщо кiлькiсть процесiв в комунiкаторi comm_graph мен- ша вiд кiлькостi у вихiдному екомунiкаторi comm – деяким процесам може повернутись значення MPI_COMM_NULL, а якщо бiльша – виклик буде помилковим.

Для опису такого графа необхiдно заповнити наступнi структури: index[] = {2, 3, 4, 6}; edges[] = {1, 3, 0, 3, 0, 2};

пiсля цього можна створювати топологiю графа (необхiдно не менше чотирьох процесiв). int

MPI_Graph_neighbors_count(MPI_Comm comm, int rank, int nneighbors); Визначає кiлькiсть сусiдiв nneighbors прцесу з рангом rank в топологiї графа.

int MPI_Graph_neighbors(MPI_Comm comm, int rank, int maxneighbors, int neighbors[]); Визначеня рангiв безпосереднiх сусiдiв процесу з рангом rank, ранги сусiдiв повертаю- ться в масивi neighbors*+. int MPI_Graphdims_get(MPI_Comm comm, int nnodes, int nedges); - Визначення кiлькостi веошин nnodes та ребер nedges в топологiї графа пов’язаної з комунiкатором comm.

int MPI_Graph_get(MPI_Comm comm, int maxindex, int maxedges, int index[], int edges[]); 3

Отримання iнформацiї про топологiю графа, котра пов’язана з комунiкатором comm. В масивах index та edges повертається опис топологiї, maxindex, maxedges – мiстять обмеже- ння на розмiри вiдповiдних масивiв (можна одержати за допомогою MPI_Graphdims_get).

1. Написати приклад MPI програми котра надрукує номера процесів та імена процесорів на котрих працює. Навести команди компіляції та запуску MPI програми.

#include

#include

int main(int argc, char **argv)

{ int size, rank, i;

MPI_Init(&argc, &argv);

MPI_Comm_size(MPI_COMM_WORLD, &size);

MPI_Comm_rank(MPI_COMM_WORLD, &rank);

char processor_name[MPI_MAX_PROCESSOR_NAME];

int name_len;

MPI_Get_processor_name(processor_name, &name_len);

if(rank == 0) printf("Total processes count = %d\n", size);

printf("I am %d process from %d (%s) processes!\n", rank, size, processor_name);

MPI_Finalize();

return 0; }

2. Написати приклад обміну між двома процесами з використанням функцій блокованого обміну.

#include

#include

int main(int argc, char **argv)

{ int nproc, my_rank;

MPI_Init(&argc, &argv);

MPI_Comm_size(MPI_COMM_WORLD, &nproc);

MPI_Comm_rank(MPI_COMM_WORLD, &my_rank);

if (my_rank == 0) {

MPI_Send ("Hello proces 1!", 15, MPI_CHAR, 1, 77, MPI_COMM_WORLD);

printf("Message send by proc %d.\n", my_rank);

} else if (my_rank == 1) { char recv_buffer[15];

MPI_Status status;

MPI_Recv (recv_buffer, 15, MPI_CHAR, 0, 77, MPI_COMM_WORLD, &status); printf("Message received by proc %d.\n", my_rank); printf("Message: %s\n", recv_buffer);

} MPI_Finalize(); return 0; }

3. Написати приклад обміну між парними та непарними процесами з використанням функцій блокованого обміну.

#include

#include

int main(int argc, char **argv)

{ int nproc, my_rank;

MPI_Init(&argc, &argv);

MPI_Comm_size(MPI_COMM_WORLD, &nproc);

MPI_Comm_rank(MPI_COMM_WORLD, &my_rank);

if (my_rank%2 == 0) {

char str[] = "Hello proces %d!"; char str2[20];

sprintf(str2,str,my_rank + 1);

MPI_Send (str2, 20, MPI_CHAR, my_rank + 1, 77, MPI_COMM_WORLD);

printf("Message send by proc %d.\n", my_rank);

}

else if (my_rank%2 == 1) {

char recv_buffer[15];

MPI_Status status;

MPI_Recv (recv_buffer, 20, MPI_CHAR, my_rank - 1, 77, MPI_COMM_WORLD,

&status);

printf("Message received by proc %d.\n", my_rank); printf("Message: %s\n", recv_buffer);

}

MPI_Finalize();

return 0;

}

4. Написати приклад обміну між двома процесами з використанням функцій неблокуючого (асинхронного) обміну.

#include

#include

int main(int argc, char **argv)

{ int nproc, my_rank;

MPI_Init(&argc, &argv);

MPI_Comm_size(MPI_COMM_WORLD, &nproc);

MPI_Comm_rank(MPI_COMM_WORLD, &my_rank);

if (my_rank == 0) {

MPI_Request request;

MPI_Status status;

MPI_Isend ("Hello proces 1!", 15, MPI_CHAR, 1, 77,

MPI_COMM_WORLD, &request);

MPI_Wait (&request, &status); printf("Message send by proc %d.\n", my_rank);

} else if (my_rank == 1) {

char recv_buffer[15]; MPI_Request request;

MPI_Status status;

MPI_Irecv (recv_buffer, 15, MPI_CHAR, 0, 77, MPI_COMM_WORLD,

&request);

printf("Message received by proc %d.\n", my_rank); MPI_Wait (&request, &status); printf("Message: %s\n", recv_buffer);

}

MPI_Finalize();

return 0;

}

5. Написати приклад обміну між парними та непарними процесами з використанням функцій неблокуючого (асинхронного) обміну.

#include

#include

int main(int argc, char **argv)

{ int nproc, my_rank;

MPI_Init(&argc, &argv);

MPI_Comm_size(MPI_COMM_WORLD, &nproc);

MPI_Comm_rank(MPI_COMM_WORLD, &my_rank);

if (my_rank%2 == 0) {

char str[] = "Hello proces %d!"; char str2[20];

sprintf(str2,str,my_rank + 1);

MPI_Request request;

MPI_Status status;

MPI_Isend (str2, 20, MPI_CHAR, my_rank + 1, 77,

MPI_COMM_WORLD, &request);

MPI_Wait (&request, &status);

printf("Message send by proc %d.\n", my_rank);

} else if (my_rank%2 == 1) {

char recv_buffer[20]; MPI_Request request;

MPI_Status status;

MPI_Irecv (recv_buffer, 20, MPI_CHAR, my_rank - 1, 77,

MPI_COMM_WORLD, &request);

printf("Message received by proc %d.\n", my_rank); MPI_Wait (&request, &status); printf("Message: %s\n", recv_buffer);

}

MPI_Finalize();

return 0;

}

6. Написати приклад створення MPI структури з трьома полями.

#include

#include

#include

#include

typedef struct{ char name[20]; int year; int mark; } UserStruct;

int main(int argc, char ** argv){

int NUMBER_OF_PROCS, RANK_OF_CURRENT, NEXT_RANK, PREV_RANK;

MPI_Status status;

UserStruct us;

MPI_Datatype us_type;

int len[4] = {10, 1, 1, 1};

MPI_Aint pos[4] = {offsetof(UserStruct, name), offsetof(UserStruct, year), offsetof(UserStruct, mark), sizeof(us) };

MPI_Init(&argc, &argv);

MPI_Datatype type[4] = {MPI_CHAR, MPI_INT, MPI_INT, MPI_UB};

MPI_Type_create_struct(4, len, pos, type, &us_type);

MPI_Type_commit(&us_type);

UserStruct send_buf = {"---------Ваше ім’я-----------", 1994, 4};

UserStruct recv_buf;

int size_of_data= 1, msg_tag = 55;

MPI_Comm_size(MPI_COMM_WORLD, &NUMBER_OF_PROCS);

MPI_Comm_rank(MPI_COMM_WORLD, &RANK_OF_CURRENT);

NEXT_RANK = RANK_OF_CURRENT == NUMBER_OF_PROCS - 1 ? MPI_PROC_NULL :

RANK_OF_CURRENT + 1;

PREV_RANK = RANK_OF_CURRENT == 0 ? MPI_PROC_NULL : RANK_OF_CURRENT - 1;

MPI_Sendrecv(&send_buf, size_of_data, us_type, NEXT_RANK, msg_tag,

&recv_buf, size_of_data, us_type, PREV_RANK, msg_tag,

MPI_COMM_WORLD, &status);

printf("Proc: %d, From: %d, To: %d, Name: %s, Year: %d, Mark: %d \n",

RANK_OF_CURRENT, PREV_RANK, NEXT_RANK, recv_buf.name, recv_buf.year, recv_buf.mark);

MPI_TYPE_FREE(&us_type)

MPI_Finalize();

return 0;

}

7. Написати приклад пересилки прийому запакованих типiв даних

#include "mpi.h"

#include

int main(int argc, char *argv[])

{

int rank, size;

int i;

char c[100];

char buffer[110];

int position = 0;

MPI_Status status;

MPI_Init(&argc, &argv);

MPI_Comm_size(MPI_COMM_WORLD, &size);

if (size < 2)

{

printf("Please run with 2 processes.\n");fflush(stdout);

MPI_Finalize();

return 1;

}

MPI_Comm_rank(MPI_COMM_WORLD, &rank);

if (rank == 0)

{

for (i=0; i<100; i++)

c[i] = i;

i = 123;

MPI_Pack(&i, 1, MPI_INT, buffer, 110, &position, MPI_COMM_WORLD);

MPI_Pack(c, 100, MPI_CHAR, buffer, 110, &position, MPI_COMM_WORLD);

MPI_Send(buffer, position, MPI_PACKED, 1, 100, MPI_COMM_WORLD);

}

if (rank == 1)

{

MPI_Recv(buffer, 110, MPI_PACKED, 0, 100, MPI_COMM_WORLD, &status);

MPI_Unpack(buffer, 110, &position, &i, 1, MPI_INT, MPI_COMM_WORLD);

MPI_Unpack(buffer, 110, &position, c, 100, MPI_CHAR, MPI_COMM_WORLD);

printf("i=%d\nc[0] = %d\n...\nc[99] = %d\n", i, (int)c[0], (int)c[99]);fflush(stdout);

}

MPI_Finalize();

return 0; }

8. Написати приклад обміну між всіма процесами з використанням функції MPI_Bcast.

#include

#include

#define N 5

int main(int argc , char** argv)

{

int rank, size;

char* msg;

MPI_Init(&argc, &argv);

MPI_Comm_size(MPI_COMM_WORLD, &size);

MPI_Comm_rank(MPI_COMM_WORLD, &rank);

if(rank == 0){ msg = "Heil to all!";

}

MPI_Barrier(MPI_COMM_WORLD);

MPI_Bcast(&msg, 11, MPI_CHAR, 0, MPI_COMM_WORLD);

if(rank != 0)

{

printf("Proc %d received\t: %s \nProc %d says\t: Heil master process!\n", rank, msg, rank);

}

MPI_Finalize();

return 0;

}

9.Написати приклад додавання квадратних матриць з використанням колективних функцій.

#include

#include

#define N 5

int main(int argc , char** argv)

{

int rank, i, j, size; double Mtx1[N][N], Mtx2[N][N], Mtx_sum[N][N]; double row1[N], row2[N], row_sum[N];

MPI_Init(&argc, &argv);

MPI_Comm_size(MPI_COMM_WORLD, &size);

MPI_Comm_rank(MPI_COMM_WORLD, &rank);

if (rank == 0)

{

for (i=0; i

for (j=0; j

Mtx1[i][j]=(i-2)*(j-5);

Mtx2[i][j]=(i-2)*(j-5);

} }

MPI_Scatter(Mtx1, N, MPI_DOUBLE, row1, N, MPI_DOUBLE, 0, MPI_COMM_WORLD);

MPI_Scatter(Mtx2, N, MPI_DOUBLE, row2, N, MPI_DOUBLE, 0,

MPI_COMM_WORLD);

for (i = 0; i < N; i++) {

row_sum[i] = row1[i] + row2[i]; if(rank == 0)printf("%d, max %lf\n", rank, row_sum[i]);

}

MPI_Gather(row_sum, N, MPI_DOUBLE, Mtx_sum, N, MPI_DOUBLE, 0,

MPI_COMM_WORLD);

if (rank == 0)

{

for (i=0; i

{

for (j=0; j

{

printf("%lf\t", Mtx_sum[i][j]);

}

printf("\n");

} }

MPI_Finalize(); return 0; }

10. Написати приклад знаходження суми максимальних елементiв рядкiв матриці з використанням колективних функцій.

#include

#include

#define N 5

int main(int argc , char** argv)

{

int rank, i, j, size; double Mtx[N][N], c[N]; double row[N]; double max_row, sum;

MPI_Init(&argc, &argv);

MPI_Comm_size(MPI_COMM_WORLD, &size);

MPI_Comm_rank(MPI_COMM_WORLD, &rank);

if (rank == 0)

{ for (i=0; i

for (j=0; j

Mtx[i][j]=(i-2)*(j-5);

}

MPI_Scatter(Mtx, N, MPI_DOUBLE, row, N, MPI_DOUBLE, 0, MPI_COMM_WORLD);

max_row = row[0];

for (i = 0; i < N; i++)

{

if (row[i]>max_row)

{ max_row = row[i]; } }

printf("%d, max %lf\n", rank, max_row);

MPI_Gather(&max_row, 1, MPI_DOUBLE, c, 1, MPI_DOUBLE, 0, MPI_COMM_WORLD);

if (rank == 0) { sum = 0;

for (i=0; i

sum += c[i];

printf("Sum of max row element : %lf \n",sum);

}

MPI_Finalize();

return 0; }

11. Написати приклад знаходження суми елементiв матриці з використанням функції MPI_Reduce.

#include

#include

#define N 5

int main(int argc , char** argv)

{

int rank, i, j, size; double Mtx[N][N], a[N], b[N];

MPI_Init(&argc , &argv ) ;

MPI_Comm_size(MPI_COMM_WORLD, &size);

MPI_Comm_rank(MPI_COMM_WORLD, &rank);

for(i = 0; i < N; i++) for(j = 0; j < N; j++)

Mtx[i][j] = 1;//(i-2)*(j-5);

MPI_Barrier(MPI_COMM_WORLD);

MPI_Allreduce(Mtx, a, N, MPI_DOUBLE, MPI_SUM, MPI_COMM_WORLD);

MPI_Reduce(a, b, N, MPI_DOUBLE, MPI_SUM, 0, MPI_COMM_WORLD);

if (rank==0) printf("Sum=%lf\n",b[0]);

MPI_Finalize();

return 0;

}

12.Написати приклад знаходження максимума елементiв вектора з використанням функції MPI_Reduce.

#include

#include

#define N 10

int main(int argc , char** argv)

{ int rank, i, size; double a[N] , b[N];

MPI_Init(&argc , &argv ) ;

MPI_Comm_size(MPI_COMM_WORLD, &size);

MPI_Comm_rank(MPI_COMM_WORLD, &rank);

for(i = 0; i < N; i++) a[i] = -(i-2)*(i-2);

MPI_Barrier(MPI_COMM_WORLD);

MPI_Reduce(a, b, N, MPI_DOUBLE, MPI_MAX, 0, MPI_COMM_WORLD);

if (rank==0) printf("Max=%lf\n",b[0]);

MPI_Finalize();

return 0;

}

Декатрова топологія в MPI.

Топологія графа в MPI.

1. Написати приклад MPI програми котра надрукує номера процесів та імена процесорів на котрих працює. Навести команди компіляції та запуску MPI програми.

2. Написати приклад обміну між двома процесами з використанням функцій блокованого обміну.

3. Написати приклад обміну між парними та непарними процесами з використанням функцій блокованого обміну.

4. Написати приклад обміну між двома процесами з використанням функцій неблокуючого (асинхронного) обміну.

5. Написати приклад обміну між парними та непарними процесами з використанням функцій неблокуючого (асинхронного) обміну.

6. Написати приклад створення MPI структури з трьома полями.

7. Написати приклад пересилки прийому запакованих типiв даних

8. Написати приклад обміну між всіма процесами з використанням функції MPI_Bcast.

9. Написати приклад додавання квадратних матриць з використанням колективних функцій.

10.Написати приклад знаходження суми максимальних елементiв рядкiв матриці з використанням колективних функцій.

11. Написати приклад знаходження суми елементiв матриці з використанням функції MPI_Reduce.

12.Написати приклад знаходження максимума елементiв вектора з використанням функції MPI_Reduce.

13.Написати приклад створення комунікатора (новий не містить процеси 0,1).

14.Написати приклад створення комунікатора (новий містить тільки процеси 0,1).

SIMULATE

;Система має 5 обслуговуючих каналів

chas VARIABLE 100; закінчення часу роботи

t_z VARIABLE 2; час бробки заяв

gus VARIABLE 10; густина заявок

GENERATE V$chas

TERMINATE 1

GENERATE (Exponential(2,0,2/V$gus))

Chan1 GATE NU 1,Chan2

SEIZE 1

ADVANCE V$t_z

RELEASE 1

TRANSFER ,done

Chan2 GATE NU 2,failed

SEIZE 2

ADVANCE V$t_z

RELEASE 2

TRANSFER ,done

done QUEUE done_count

TRANSFER ,ex

failed QUEUE failed_count

TRANSFER ,ex

ex TERMINATE

Загальна структура MPI програми. Отримання інформації про розмір комунікатора, ранг процесу.

Найбiльш загальним пiдходом при створеннi паралельних програм в даний час є застосу- вання бiблiотеки передачi повiдомлень, де процеси використовують звернення до бiблiотеки MPI (Message Passing Interface), щоб обмiнюватися повiдомленнями (iнформацiєю) з iншими процесами. Механiзм передачi повiдомлень дозволяє процесам, запущеним на ба- гатопроцесорнiй системi, спiльно вирiшувати великi завдання. Iснує декiлька функцiй, якi використовуються в будь-якому, навiть самому короткому додатку MPI. Займаються вони не стiльки власне передачею даних, скiльки її забезпеченням:

Iнiцiалiзацiя бiблiотеки.MPI_Init( &argc, &argv );

Аварiйне закриття бiблiотеки. Викликається, якщо програма користувача завершує- ться через помилку часу виконання, пов’язаних з MPI:MPI_Abort();

Нормальне закриття бiблiотеки:MPI_Finalize();

Двi iнформацiйнi функцiї: повiдомляють розмiр групи (тобто загальну кiлькiсть зав- дань, пiд’єднаних до її областi зв’язку) i порядковий номер завдання: int size , rank;

MPI_Comm_size( MPI_COMM_WORLD, &size );

MPI_Comm_rank( MPI_COMM_WORLD, &rank );

Сем. Orchidaceae – Ятрышниковые, или Орхидные
Пітримання установленого ритму виробництва
The concept and the legal status of refugee. The United Nations Convention relating to the Status of Refugees 1951
Условие первое - внимательно смотрите на мяч
Освітні послуги в Одеський області
Конструирование системы отопления
Мероприятия по борьбе с вредителями и болезнями роз закрытого грунта.
Глобальные проблемы современной цивилизации (1 час)
Понятие метода, методологии и методики
II. Reading
Exercise 3.5
Субъекты таможенного права: понятие, виды.
Класний керівник Мірошниченко С.В., Божко Т.М.
Государство и личность. Понятие правового статуса личности, его структура
Особливості формування та розвитку світового ринку праці
Вопрос: пенсионный фонд России и фонд социального страхования их формирование функции и использование.
Химические свойства соединения хрома и марганца.
Экономика и управление на предприятии (по отраслям)»
Форми судового процесу
Creating Symbols
Постсоціалістичні країни перехідної економіки.
Создание описаний отдельных блоков проекта
Трансформації політичного режиму в повоєнній Україні.
Главная Страница