Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Julia - get real part of complex array

Tags:

arrays

julia

I need to split the variable z::Array{Complex128,1} into two arrays for the real and complex parts. One way do this is to make new variables ::Array{Float64,1} and fill them element by element:

for i = 1:size(z)[1]
    ri[i] = z[i].re
    ii[i] = z[i].im
end

Is there a way to do this that doesn't involve copying data, like somehow manipulating strides and offsets of z?

like image 281
Matthew Bedford Avatar asked Sep 15 '16 14:09

Matthew Bedford


1 Answers

In the common case where copying is not an issue, just do real.(z) and imag.(z). I include this to help future readers who have a similar issue, but who might not care about copying.

As you suggest, you can manipulate strides of z to avoid copying data. Simply

zfl = reinterpret(Float64, z)
zre = @view zfl[1:2:end-1]
zim = @view zfl[2:2:end]

Combined, we observe that there is no data copying (the allocations are due to the heap-allocated array views, and are minimal).

julia> z = Vector{ComplexF64}(100000);

julia> function reimvec(z)
           zfl = reinterpret(Float64, z)
           zre = @view zfl[1:2:end-1]
           zim = @view zfl[2:2:end]
           zre, zim
       end
reimvec (generic function with 1 method)

julia> @time reimvec(z);
  0.000005 seconds (9 allocations: 400 bytes)

As we can see, behind the scenes, such an array is strided:

julia> strides(reimvec(z)[1])
(2,)
like image 82
Fengyang Wang Avatar answered Nov 19 '22 03:11

Fengyang Wang