Making mapslices drop dimensions for scalars results automatially

In a sense, I am looking for a workaround for #16606: for functions which return an array, I would like to keep it as is, but for functions which return a scalar, I would like to drop the relevant dimension. I can’t just apply dropdims automatically, eg

using Statistics
R = randn(100, 5)
mapslices(col -> quantile(col, [0.25, 0.5, 0.75]), R; dims = 1) # size (3, 5), OK
mapslices(col -> quantile(col, [0.5]), R; dims = 1)             # size (1, 5), OK
mapslices(mean, R; dims = 1)                                    # size (1, 5), I want (5, )
1 Like

On Julia 1.1, you can use map(mean, eachslice(R, dims=1)). Now, that won’t do the concatenating behavior in the other cases (it’ll make an array of arrays), but I find that much easier to reason about. :slight_smile:

4 Likes

This answer is incorrect. The functions mapslices and eachslice seem to work differently (and inconsistently?). Note how I need to change dimension to obtain the same result.


julia> mat = rand(3,4);

julia> map(sum , eachslice(mat ; dims=1))
3-element Array{Float64,1}:
 2.2826198339269235
 2.681128756495633 
 2.108886303861928

julia> dropdims(mapslices(sum, mat ; dims=2); dims = 2 )
3-element Array{Float64,1}:
 2.2826198339269235
 2.681128756495633 
 2.108886303861928 

In case of arrays of 3 dimensions or more, I am not sure it’s possible to find the equivalent form of eachslice.

1 Like

For doing many dimensions you may want JuliennedArrays, which appears to follow the convention of mapslices:

julia> using JuliennedArrays

julia> map(sum, Slices(mat, 2)) == map(sum, eachslice(mat; dims=1))
true

julia> map(sum, Slices(rand(10,20,30,40), 1,3)) |> size
(20, 40)
2 Likes