I’ve been thinking about a pattern that often comes up when I write Julia code. I frequently find myself creating a vector and then appending elements to that vector within a loop. But that raises the question of how to declare the element type of the vector. Let’s be concrete. Suppose I have a function f(i)
and I want to call it multiple times and collect the results. I can do the following:
results = []
for i in 1:10
push!(results, f(i))
end
but this makes results
a Vector{Any}
, which is sub-optimal. If the return type of f(i)
is obvious, then I can use it in my declaration:
results = T[]
for...
end
but often times that return type is not obvious, or is just heavily parameterized and tedious to type out. If I still want a concretely-typed results vector, then I can try to manually invoke Core.inference
, but that’s not exported and can be tedious, since it requires deriving the types of the inputs to f()
myself.
There’s another option, which is to use the comprehension syntax:
[f(i) for i in 1:10]
which is perfect for loops with short bodies but less convenient if the loop body is complex.
What I actually want (I think), is to be able to do something like:
results = <future T>[]
for i in 1:10
push!(results, f(i)::<future T>)
end
where <future T>
is a type that has to be figured out based on the type inference of f(i)
later in the function (thus, in the “future” (not in the world-age sense, though)).
So, my question is: is this possible? Clearly if the inferred type of f(i)
depends on the type of results
, then the answer is no. But if the type of f(i)
is independent of results
, then it should at least be computable. In a sense, this is just a matter of trying to save the user from having to manually invoke inference.
Anyway, this is all just fairly wild speculation, but I’m curious if others have found themselves wanting something similar or if there’s a way to get what I want without changing Julia itself.