【问题标题】:Julia: How to create a symbol inside a function that matches the input variable?Julia:如何在与输入变量匹配的函数中创建符号?
【发布时间】:2017-01-02 07:36:11
【问题描述】:

我有一个 Julia 函数,它接受一些输入参数并使用它们来执行多个操作。为了使这些操作之一正常工作,我需要能够计算与用户输入匹配的符号。例如函数看起来像这样:

function func(arg1,arg2)

    symb_arg1 =  ## get the symbol for input into arg1
    symb_arg2 =  ## get the symbol for input into arg2

    println(symb_arg1)
    println(symb_arg2)

    ## Do some operations using arg1, arg2, symb_arg1, symb_arg1

end

我希望实现以下行为:

a = 25
b = rand(27,55,18)
func(a,b)  ## prints :a and :b

这里的困难是让函数计算一个包含变量实际名称的符号,而不是变量的值。这个post 提供了以下宏,几乎可以满足我的要求:

macro mymacro(ex)
    Expr(:quote,ex) # this creates an expression that looks like :(:(x + 2))
end

此宏适用于执行以下操作:

a = rand(27,15)
symb_a = @mymacro(a)  ## prints :a

但是,在我的函数中使用这个宏不会产生预期的效果。具体来说,如果我将我的功能定义为:

function func_bad(arg1,arg2)

    symb_arg1 = @mymacro(arg1)
    symb_arg2 = @mymacto(arg2)

    println(symb_arg1)
    println(symb_arg2)

    ## Do some operations using arg1, arg2, symb_arg1, symb_arg1

end

然后运行命令:

a = 25
b = rand(27,55,18)
func_bad(a,b)  ## prints :arg1 and :arg2 (instead of the desired :a and :b)

当然,一种简单(但不那么优雅)的解决方案是为函数添加额外的输入参数,以便用户负责创建符号。然而,这更像是最后的手段。我希望该功能能够自动创建符号。关于如何修改函数或宏以实现此行为的任何想法?

【问题讨论】:

    标签: macros julia


    【解决方案1】:

    简单的答案是这是不可能的;有一个抽象屏障阻止函数看到调用者的实现细节。他们得到的只是值,这是稳健和清晰程序的关键属性。

    您可以做的一件事是编写一个宏来转换呼叫站点:

    @with_syms func(a, b)
    

    变成类似的东西

    func((:a,a), (:b,b))
    

    将符号-值对传递给函数。

    另一个稍微不同的设计是为所有需要此行为的函数提供宏包装器,以便调用看起来像@func(a,b)。您可以将参数列表转换分解为辅助函数;每个宏看起来像

    macro func(args...)
        :(func($(pair_with_symbols(args)...)))
    end
    

    【讨论】:

    • 我怀疑这可能是不可能的。不过,看起来我可以使用您的一种替代方案来摆脱困境 - 谢谢!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-11-17
    • 1970-01-01
    • 2020-08-08
    • 1970-01-01
    • 2012-07-04
    相关资源
    最近更新 更多