在宏内部使用Julia的外部命令插值?

时间:2014-10-31 17:43:29

标签: julia

我一直在尝试编写一个Julia宏,它接受Cmd对象并在循环中运行它们。问题是我想在命令中使用本地循环变量进行插值。我会编写一个函数并使用eval(),但eval()使用全局范围,因此无法看到本地循环变量。

下面是一个简单的例子,演示字符串插值的工作原理,但命令插值失败:

macro runcmd(cmdExpr)
    quote
        for i in 1:2
            println("i: $i")
            run($cmdExpr)
        end
    end
end
@runcmd(`echo $i`)

输出

i: 1
ERROR: i not defined
 in anonymous at none:5

如果我扩展宏,我会

quote  # none, line 3:
    for #261#i = 1:2 # line 4:
        println("i: $#261#i") # line 5:
        run(Base.cmd_gen((("echo",),(i,))))
    end
end

我猜测cmd_gen参数中缺少的#261#部分对i的引用与问题有关,但我不确定。

1 个答案:

答案 0 :(得分:1)

您是对的,问题是由于索引#261#iecho $i中对其的引用不匹配。解决问题的一种简单方法是转义索引中使用的i

macro runcmd(cmdExpr)
    quote
        for $(esc(:i)) in 1:2
            println("i: $i")
            run($cmdExpr)
        end
    end
end

然后我们得到:

julia> @runcmd(`echo $i`)
i: 1
1
i: 2
2

朱莉娅的metaprogramming documentation还有更多讨论。