local nt = @eval $x
for k in keys(nt)
local v = nt[k]
@eval $k = $v
p = (a=1, b="b")
julia> @unp p
Unpack a NamedTuple and create new variables in the calling scope. I know, that’s unsafe, and it is not that I actually need it, but I’m curious how can that be done. In the example above it works. How can that be done if the macro called in a different scope?
No, we mean that eval always evaluate on global scope, and therefore your function will always create global variables. If you call it inside a function it will not create variables local to the function, and if the function had any local variables of the same name they will be shadowing such global variables. What you see only work because you are working in global scope in the REPL.
julia> function unp(x)
exs = [Expr(:(=), k, QuoteNode(x[k])) for k in keys(x)]
unp (generic function with 1 method)
julia> function test_unp(p)
a = 10
b = "c"
test_unp (generic function with 1 method)
julia> test_unp((a=1, b="b"))
a = 10
b = "c"
Here you can see that the variables are global (appeared out of the function that called unp) and that the local variables shadowed them inside the function.
If we do not define a local a and a local b inside the test_unp function, then the function see the global variables, but I am not sure this works outside of the REPL. Julia has something called “Age of the world” that sometimes prevents things just evaluated to be used immediately in the sequence.