Efficient conversion from StaticArray to Base Array?

Hello!

Suppose I have an array defined as such:

using StaticArrays
b = Array{StaticArrays.SArray{Tuple{3},Float32,1,3},1}([[1,1,1],[2,2,2],[3,3,3]])

And I want it to be transformed to a convential:

 Array{Array{Float32,3},1}

I have not found an efficient way to do so, and my approach using iterators gives me a very high amount of allocations…

The reason I want to do this in the first place is that I am interfacing with a Julia library which interfaces with something else, and it needs to be fed standard arrays.

Kind regards

What do you mean by a high amount of allocations. If you have a Vector of SArray and wants to create from it a Vector of Array, you will need to make an allocation for each new Array (i.e., for each element of the outer vector).

SArray is a static array, this means it is possible that a Vector of SArrays is stored contiguously inside the Vector and just one allocation is done. For a Vector or Array you almost surely will have each element as a “pointer” to a heap object allocated separately. Again, SArray is immutable, Arrays is mutable, do you need the mutability? If you need it maybe the best solution is to have a single 4-dimensional Array, instead of a Vector of 3-dimensional SArrays.

2 Likes

Sorry, I might not have explained it properly. I ended up fixing my mistake:

using StaticArrays

x = zeros(100)

r = [rand(3,1) for i in x]

b = Array{StaticArrays.SArray{Tuple{3},Float32,1,3},1}(r)

@time b_flat = collect(Iterators.flatten(Iterators.flatten(b)))

nr = size(b)[1]
nc = size(b[1])[1]

# I had changed place of nr and nc, so that gave much higher allocations
@time b_arr  = reshape(b_arr,(nr,nc))

This code gives very few allocations and does what I want. If one can improve it I would like to learn

Kind regards

I do not need mutability as such, I just need in the shape of a typical Julia array to work properly with the external package.

Kind regards

reinterpret(Float32, b') might work, give it a whirl.

3 Likes

Thanks that indeed worked! Any suggestions of how to get the type, other than doing:

typeof(b[1][1])
Float32

Kind regards

eltype(eltype(b))

1 Like