Fast array indexing

What is the most efficient way to access (and possibly replace) records in a large multidimensional array? I am using something like this inside a loop:

tup = (16,45,6,40,3)
A[tup...] = 100

but I am wondering if there is a more efficient way. In particular, is there a way to avoid use ...?

+4
source share
3 answers

Not always the punishment associated with splatting, but determining where it is effective is not always obvious (or easy). Your trivial example is actually as efficient as writing A[16,45,6,40,3] = 100. You can see it by comparing

   function f(A)
       tup = (16,45,6,40,3)
       A[tup...] = 100
       A
   end
   function g(A)
       A[16,45,6,40,3] = 100
       A
   end
julia> code_llvm(f, Tuple{Array{Int, 5}})
# Lots of output (bounds checks).
julia> code_llvm(g, Tuple{Array{Int, 5}})
# Identical to above

, . @allocated code_llvm @jl_pgcstack - , . , , , , splatting. , , ... splatting. @code_warntype, . , :

   function h(A)
       tup = ntuple(x->x+1, 5) # type inference doesn't know the type or size of this tuple
       A[tup...] = 100
       A
   end
julia> code_warntype(h, Tuple{Array{Int,5}})
# Lots of red flags

, , tup.

+5

, for index in eachindex(A); ., ,

https://groups.google.com/forum/#!msg/julia-users/CF_Iphgt2Wo/V-b31-6oxSkJ

A - , , ( ):

A = rand(3, 3)

for i in eachindex(A)
   println(i)
end

, A , . subarray, eachindex(A) :

julia> for i in eachindex(slice(A, 1:3, 2:3))
           println(i)
       end

CartesianIndex{2}((1,1))
CartesianIndex{2}((2,1))

.

+5

- .
Base.Base.linearindexing - Base, .

julia> a=rand(1:10...);
julia> Base.Base.linearindexing(a)
Base.LinearFast()

You can use the syntax ii=sub2ind(size(A),tup...)to convert an index tuple to a single linear index or for i in eachindex(A)to move it.

-1
source

Source: https://habr.com/ru/post/1618245/


All Articles