我在 Julia 中找到了一个unless
宏示例,如下所示:
macro unless(test, branch)
quote
if !$test
$branch
end
end
end
但是,当我尝试使用它时,它会失败(显然存在卫生问题,但我无法准确弄清楚)。这是我使用的测试:
x, y = 0, 1
@unless (x == 5) begin # should execute
y = 3
end
@unless (x == 0) begin # should not execute
y = 5
end
@assert y == 3 # FAILS! SAYS y is 0
现在我可以通过只转义分支而不是测试来完成这项工作:
macro unless(test, branch)
quote
if !$test
$(esc(branch))
end
end
end
我的问题是:为什么只逃避分支而不是测试就足够了?现在我确实尝试了宏扩展。在第一种情况下,没有esc
,我得到这个:
julia> macroexpand(:(@unless (x == 5) begin y = 3 end))
quote # none, line 3:
if !(x == 5) # none, line 4:
begin # none, line 1:
#2#y = 3
end
end
end
现在,即使没有一个宏参数被转义,只有y
gensymed !谁能解释为什么会这样?(我知道第二个版本有效,因为当我逃离分支时, y 没有得到 gensymed 并且宏y = 3
按预期扩展。但我完全不知道为什么x
即使没有 gensymed 也没有使用esc
。)