I wonder if there is an API for testing if something returned by to_indices is a “scalar” index (ie one that would drop dimensions). I could not find anything, and I think it would be useful to have, and thought I would ask here before making a PR before the 1.2 feature freeze.
One can of course rely on the documentation and note that currently “scalar” indexes are Int or CartesianIndex. But this may change in the future, just like CartesianIndex was introduced.
The proposal is something trivial like
is_scalar_index(::Integer) = true
is_scalar_index(::CartesianIndex) = true
is_scalar_index(_) = false
An MWE for some context is
"""
Wrapper for vectors, supports subsetting via [].
"""
struct Foo
a # both are <: AbtractVector, but here omit
b # type parameters to simplify example
function Foo(a, b)
@assert axes(a) == axes(b)
new(a, b)
end
end
Base.firstindex(f::Foo) = firstindex(f.a)
Base.lastindex(f::Foo) = lastindex(f.a)
function Base.getindex(f::Foo, i)
ι = first(to_indices(f.a, (i, )))
if ι isa Union{Integer, CartesianIndex} # this would be more robust
error("subset using non-scalar indexes")
else
Foo(f.a[ι], f.b[ι])
end
end
with
julia> f = Foo(1:5, ones(5))
Foo(1:5, [1.0, 1.0, 1.0, 1.0, 1.0])
julia> f[2:3]
Foo(2:3, [1.0, 1.0])
julia> f[2]
ERROR: subset using non-scalar indexes
Stacktrace:
[1] error(::String) at ./error.jl:33
[2] getindex(::Foo, ::Int64) at ./REPL[19]:4
[3] top-level scope at REPL[27]:1