2.4 Примеры программ

Для того, чтобы окончательно уяснить для себя принципы работы с OpenMP, далее приведен простой, но достаточно емкий пример параллельного вычисления числа пи с приминением OpenMP:

#include <stdio.h> 
#include <math.h> 
#include <omp.h> 
 
int main() 
{ 
    const int N = 10000000; 
    const double L = 1.0; 
    const double h = L / N; 
    const double x_0 = 0.0; 
 
    double pi; 
    double t_1, t_2; //временные интервалы 
 
    int i; 
    double sum = 0.0; 
 
    t_1 = omp_get_wtime(); //начальный замер времени

Инициализируем параллельную область для основного блока вычислений, используя директиву parallel for с опциями reduction и schedule:

#pragma omp parallel for reduction(+: sum) schedule(static) 
    for (i = 0; i < N; ++i) 
    { 
        double x = x_0 + i * h + h/2; 
        sum += sqrt(1 - x*x); 
    }

Делаем конечный замер времени и выводим результаты на экран:

    t_2 = omp_get_wtime(); 
 
    pi = sum * h * 4.0; 
 
    printf("omp_get_max_threads(): %d\n", omp_get_max_threads()); 
    printf("time: %f\n", t_2 - t_1); 
    printf("pi ~ %f\n", pi); 
 
    return 0; 
}

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

Задаем три матрицы размерностью 4096×4096 элементов каждая, первые две инициализируются, в третью записывается результат полученных вычислений.

#include <stdio.h> 
#include <omp.h> 
 
#define N 4096 
 
double a[N][N], b[N][N], c[N][N]; 
 
int main() 
{ 
   int i, j, k; 
   double t1, t2; //временные интервалы

Инициализируем матрицу, замеряем время начала работы основного вычислительного блока:

   for (i = 0; i < N; i++) 
      for (j = 0; j < N; j++) 
         a[i][j] = b[i][j] = i * j; 
 
   t1=omp_get_wtime();

Основной вычислительный блок, массивы a, b и c задаются общими, а переменные i, j и k частными. После окончания вычислений проводится очередной замер времени после которого выводится общее время выполнения программы:

#pragma omp parallel for shared(a, b, c) private(i, j, k) 
   for(i = 0; i < N; i++){ 
      for(j = 0; j < N; j++){ 
         c[i][j] = 0.0; 
         for(k = 0; k < N; k++) c[i][j] += a[i][k] * b[k][j]; 
      } 
   } 
 
   t2=omp_get_wtime(); 
 
   printf("Time=%lf\n", t2-t1); 
}