Could someone please explain the new behavior, that is somewhat counterintuitive?
Context: I want a function that takes a String as argument and, assuming that the String represents an anonymous function, checks that the anonymous function can be called with one Real argument. The goal is to then store this anonymous function and the String representing it in a structure. I read several posts telling that this is a bad idea and that there is almost certainly a better way to do it, but I could not find this better way.
You will need an invokelatest in there. Functions run in a fixed world-age, and eval will not respect that. This is (part of) why people tell you not to write code this way.
I’ll also point out that the ‘change in behaviour’ was actually a bugfix, since the answer you got on version 1.9 and below was actually incorrect. The function you created was not callable in that worldage
Here’s a demo:
julia> VERSION
v"1.9.4"
julia> function foo(s)
f = eval(Meta.parse(s))
@show hasmethod(f, (Real,))
@show f(1)
end;
julia> foo("x -> x")
hasmethod(f, (Real,)) = true
ERROR: MethodError: no method matching (::var"#7#8")(::Int64)
The applicable method may be too new: running in world age 33477, while current world is 33478.
whereas on v1.10 and up:
julia> VERSION
v"1.11.3"
julia> function foo(s)
f = eval(Meta.parse(s))
@show hasmethod(f, (Real,))
@show f(1)
end;
julia> foo("x -> x")
hasmethod(f, (Real,)) = false
ERROR: MethodError: no method matching (::var"#1#2")(::Int64)
The applicable method may be too new: running in world age 26684, while current world is 26685.