Jouni Helske
Jouni Helske

Reputation: 6477

Fortran's do-loop over arbitary indices like for-loop in R?

I have two p-times-n arrays x and missx, where x contains arbitrary numbers and missx is an array containing zeros and ones. I need to perform recursive calculations on those points where missx is zero. The obvious solution would be like this:

do i = 1, n
   do j = 1, p
      if(missx(j,i)==0) then
         z(j,i) = ... something depending on the previous computations and x(j,i)
      end if
   end do
end do

Problem with this approach is that most of the time missx is always 0, so there is quite a lot if statements which are always true.

In R, I would do it like this:

for(i in 1:n)
  for(j in which(xmiss[,i]==0))
     z[j,i] <- ... something depending on the previous computations and x[j,i]

Is there a way to do the inner loop like that in Fortran? I did try a version like this:

do i = 1, n
   do j = 1, xlength(i) !xlength(i) gives the number of zero-elements in x(,i)
     j2=whichx(j,i) !whichx(1:xlength(i),i) contains the indices of zero-elements in x(,i)
     z(j2,i) = ... something depending on the previous computations and x(j,i)
   end do
end do

This seemed slightly faster than the first solution (if not counting the amount of defining xlength and whichx), but is there some more clever way to this like the R version, so I wouldn't need to store those xlength and whichx arrays?

Upvotes: 2

Views: 493

Answers (1)

I don't think you are going to get dramatic speedup anyway, if you must do the iteration for most items, than storing just the list of those with the 0 value for the whole array is not an option. You can of course use the WHERE or FORALL construct.

forall(i = 1: n,j = 1: p,miss(j,i)==0) z(j,i) = ...

or just

where(miss==0) z = ..

But the ussual limitations of these constructs apply.

Upvotes: 5

Related Questions