Hi everyone, I want to create a function that receives another function as an input and returns the size of the array this. As an example, let’s say I have a simple function that takes a vector as an input:
julia> f(x::Vector{<:Number}) = x[1]+x[2]
f (generic function with 1 method)
julia> g(::typeof(f)) = 2
g (generic function with 1 method)
julia> g(f)
2
Note that you probably want <:Number, not Vector{Number}.
I want my users to input an user-defined function f(x,p,q) where the sizes of x and q are not relevant, but the size of p is, because it is later given to another function as an input.
I can always ask the user to specify the size of p a priori and throw warnings/errors later in the code if the specified size is not correct, but I was wondering if there was a way to prevent these types of user error automatically in Julia.
The only thing that comes to mind is StaticArrays.jl if said arrays are small enough, but honestly I think you should go for the easy way of throwing errors
They don’t need to be small enough. We could used a SizedArray. We just need to move the size into the type domain.
julia> g(f::Function) = only(methods(f)).sig.parameters[2].body.parameters[1].parameters[1]
g (generic function with 1 method)
julia> f(x::StaticVector{2}) = x[1]+x[2]
f (generic function with 1 method)
julia> g(f)
2
julia> h(x::StaticVector{3}) = x[1]+x[2]+x[3]
h (generic function with 1 method)
julia> g(h)
3
julia> x = SizedVector{2}(rand(2))
2-element SizedVector{2, Float64, Vector{Float64}} with indices SOneTo(2):
0.5036256944197668
0.3502881692558516
julia> f(x)
0.8539138636756184
julia> y = SizedVector{3}(rand(3))
3-element SizedVector{3, Float64, Vector{Float64}} with indices SOneTo(3):
0.5070385956063957
0.8204921722209075
0.6512150701603181
julia> h(y)
1.9787458379876215
We could then create an accessory function that helps us call the arbitrary functions.
julia> function call_with_sized_view(foo, vec::AbstractVector)
foo(SizedVector{g(foo)}(@view(vec[firstindex(vec):(firstindex(vec) + g(foo) -1)])))
end
call_with_sized_view (generic function with 1 method)
julia> call_with_sized_view(f, 1:5)
3
julia> call_with_sized_view(h, 1:5)
6