OpenMP parallel for floating point range

I have the following program:

int main(){
   double sum=0;
   #pragma omp parallel for reduction(+:sum)
   for(double x=0;x<10;x+=0.1)
   sum+=x*x;
}

      

When I compile it, I get an error invalid type for iteration variable ‘x’

.

I suppose this means that I can apply the construct parallel for

to entire loops. But the internals of my loop really depend on the fact that it is a floating point.

Is there a way to convince OpenMP of this? Is there a recommended alternative method?

+3


source to share


3 answers


From comments:

No, OpenMP won't do it for you for the same reasons as in this answer asked about OpenMP loops with integer arithmetic; it is extremely difficult for the compiler to reason about floating point numbers - in particular, the compiler needs to know before injecting the loop into the tripcount loop, and the floating point arithmetic in the loop makes it very difficult at all, even if there are some simple cases it would be ok ( let's say looping 0.5-10.0).



For the same reason, even purely sequential optimization / vectorization of loops of this shape will suffer. The best way to do this is to create an equivalent integer loop and calculate your float based on the integer index;

for (int i=0; i<100; i++) { 
    double x=0.1*i; 
    sum += x*x; 
}

      

+6


source


More generally, you need to go and read What Every Computer Scientist Should Know About Floating Point Arithmetic . The fact that you are adding 0.1 and expecting exact results is evidence that you haven't read it yet :-)



0


source


The OpenMP standard defines a "for" loop only for integer, pointer and iterator types, not for floating point types:

http://www.openmp.org/wp-content/uploads/openmp-4.5.pdf#page=62

2.7.1 Loop Construct

  #pragma omp for [clause[ [,] clause] ... ] new-line
  for-loops

      

In particular, all connected loops must be in the form of a canonical cycle (see section 2.6 on page 53).

2.6 Canonical loop shape

A cycle is in the form of a canonical cycle if it matches the following:

for (init-expr; test-expr; incr-expr) structured-block

      

init-expr

One of the following:

 var = lb
 integer-type var = lb
 random-access-iterator-type var = lb
 pointer-type var = lb

      

...

incr-expr

One of the following:

++var
var++
-- var
var --
var += incr
var -= incr
var = var + incr
var = incr + var
var = var - incr

      

var

One of the following:

  • Integer variable, signed or unsigned.
  • For C ++, a variable of the random access iterator type.
  • For C, a variable of type pointer.

The canonical form allows you to calculate the number of iterations of all related loops before executing the outermost loop

So, for non-canonical types, the compiler cannot calculate the number of iterations.

0


source







All Articles