[patch, fortran, 4.9] Improve efficiency of array constructor operators

Thomas Koenig tkoenig@netcologne.de
Tue Mar 26 17:17:00 GMT 2013


Hi Tobias,

> I have not yet looked at the patch, but I wonder whether that causes
> invalid code for
>    if (any([a,b,c] < f()))
> by evaluating f() multiple times.

This is avoided by this part of the patch:

+  if (op2->expr_type == EXPR_CONSTANT)
+    scalar = gfc_copy_expr (op2);
+  else
+    scalar = create_var (gfc_copy_expr (op2));

which results in code like this:

     __var_1 = f ();
     if ((a > __var_1 || b > __var_1) || c > __var_1)
       {
         {

> Another question is: Why do we generate a temporary array for ANY/ALL?

The straightforward way of evaluating

    if (any([a,b,c] > 0.)) then

is to

- create a temporary array [a,b,c]
- to create a second logical array and fill it with the
   logical expressions,
- call a library function for ANY on it.

This was the original code and was not really efficient ;-)

Since Mikael's patch some time ago, we

- create a temporary array [a,b,c]
- loop over it, exiting early if a true value was found

With this patch (and my previous patch, which is already in),
with front-end optimization enabled, we now

- convert the expression into if (any[a>0, b>0, c>0])
- convert this into a>0 || b>0 || c>0 (effect of my previous patch)

>A
> scalar should be sufficient, i.e.
>
> res = .false.
> do i = 1, n
>    res = res .or. (array(i) < eps)
> end do
> if (res)

We have been doing that since Mikael's patch some years ago.

Regards

	Thomas



More information about the Fortran mailing list