Dear All,

Thank you so much for the various hints and tips. After re-reading the 
performance Tips I've now found all the problems with the code: in the end 
there were two type-instabilities, one that was easy to resolve (declare an 
array to be Int instead of Integer) but the other is still a problem for me 
so I'd love to get more feedback on this. (Initially I was looking for the 
wrong thing as I hadn't realised that type-instability can cause unneeded 
memory allocation.)

So my remaining issue is this. To get the code to run efficiently I had to 
tell the compile that a certain array is 2-dimensional.

   I = geom.I::Array{Int, 2}

In the type for geom, it is only declared as I::Array{Int}, because it 
could in fact be 1-, 2- or 3-dimensional. At the moment, I see two ways to 
fix this:
 * write three functions, and a wrapper which checks for the correct 
dimension. (Or possibly wrap my head around meta-programming and do it this 
way. This would probably have the advantage that I could also unroll the 
inner loops and get some additional factors)
 * replace I with a one-dimensional array and resolve the multi-dimensional 
indexing manually, probably some slow-down because of checking the dimension

BUT, is there a quicker/easier/more readable fix?

Many thanks,
    Christoph



function evalSiteFunction!(sp::SiteLinear, geom::tbgeom, 
                           Y::Array{Float64,2},
                           Frc::Array{Float64,2})
    # extract dimension information (d1, d2 \in \{2, 3\})
    I = geom.I::Array{Int, 2}
    d1, d2, nneig = size(sp.coeffs)
    # assert type of the index set over which we are looping
    for jX in geom["iMM"]::Array{Int, 1}
        # initialise force to 0
        Frc[:,jX] = 0.0
        # loop over neighbouring sites
        @inbounds for n in 1:nneig
            # get the X-index of the current neighbour
            kX = getI(I, geom.X2I, jX, sp.stencil, n) 
            # evaluate the term (devectorized for performance)
            for i = 1:d1
                Frc[i, jX] = sp.coeffs[i, 1, n] * Y[1, kX]
                for j = 2:d2
                    Frc[i,jX] += sp.coeffs[i, j, n] * Y[j, kX]
                end
            end
        end
    end
end


Reply via email to