Поделиться через


Предупреждение компилятора (уровень 4) C4938

"переменная": переменная сокращения формата с плавающей точкой может привести к несогласованным результатам при использовании /fp:strict или #pragma fenv_access

Не следует использовать /fp: strict или fenv_access с сокращениями чисел с плавающей запятой OpenMP, так как сумма вычисляется в другом порядке. Таким образом, результаты могут отличаться от результатов вычислений без использования параметра /openmp.

При компиляции следующего примера будет выдано предупреждение C4938:

// C4938.cpp
// compile with: /openmp /W4 /fp:strict /c
// #pragma fenv_access(on)
extern double *a;

double test(int first, int last) {
   double sum = 0.0;
   #pragma omp parallel for reduction(+: sum)   // C4938
   for (int i = first ; i <= last ; ++i)
      sum += a[i];
   return sum;
}

Без явной параллелизации сумма вычисляется следующим образом:

sum = a[first] + a[first + 1] + ... + a[last];

С явной параллелизацией (и двумя потоками) сумма вычисляется следующим образом:

sum1 = a[first] + ... a[first + last / 2];
sum2 = a[(first + last / 2) + 1] + ... a[last];
sum = sum1 + sum2;