In the code below, bar is an inner function. I’d like to get its type from outside the outer function foo, but without calling foo. Is that possible?
function foo()
bar() = 1
end
T = typeof(foo()) # var"#bar#8"
# is there a way to get the same thing as `T` without calling `foo`?
# I might have though something like this could work (but it doesn't):
foo.bar
Note, in my real example, foo doesn’t return bar, so I can’t use Core.Compiler.return_type.
Probably someone has a better answer than me, but I would bet on not being possible. If the closure is created inside the function, then it may not exist before the function is called and, consequently, their type also do no exist. You can’t lift the function to the global scope?
julia> function foo()
bar() = 1
end
foo (generic function with 1 method)
julia> @code_lowered foo()
CodeInfo(
1 ─ bar = %new(Main.:(var"#bar#1"))
└── return bar
)
However, perhaps he can explain why he wants that? Might be one of these cases where there is another way to deal with the actual problem.
(does that type provides any information more than just the function name?)
Interesting solutions, thanks. My main purpose is actually for AutoPrealloaction.jl which uses Cassette.jl to overdub code to preallocate memory, and to make something work, I need to write a custom overdub for an inner function of some other package, hence I need the inner function’s type.
The solution above basically works but is definitely way too internal-dependent and also not stable w.r.t. future code changes inside foo for it to be a real solution, but its certainly interesting to see it:
using Cassette
function foo()
bar() = 1
bar()
end
T = eval(@code_lowered(foo()).code[1].args[2].args[1].name)
# make bar return 2 instead
Cassette.@context Ctx
Cassette.overdub(ctx::Ctx, ::T) = 2
Cassette.overdub(Ctx(), foo) # 2, works