Julia 有函数装饰器吗?

log*_*ick 1 julia

在某些语言(如 Python)中有函数装饰器,它们看起来像宏并位于函数定义之上。装饰器为函数本身提供了一些额外的功能。

Julia 是否以任何方式支持这种函数装饰器的想法?是否可以使用宏来实现相同的目标?

use*_*164 5

这是使用ExprTools.jl使用宏实现此目的的一种方法:

import ExprTools

macro dec(decorator, inner_def)
    inner_def = ExprTools.splitdef(inner_def)
    outer_def = copy(inner_def)
    fname = get(inner_def, :name, nothing)
    if fname !== nothing
        @assert fname isa Symbol
        inner_def[:name] = Symbol(fname, :_inner)
    end
    outer_def[:body] = Expr(:call,
        :($decorator($(ExprTools.combinedef(inner_def)))),
        get(outer_def, :args, [])...,
        get(outer_def, :kwargs, [])...,
    )
    return esc(ExprTools.combinedef(outer_def))
end
Run Code Online (Sandbox Code Playgroud)
julia> _time(f) = (x...) -> (t0=time(); val=f(x...); println("took ", time()-t0, " s"); val)
_time (generic function with 1 method)

julia> @dec _time function foo(x, y)
           return x + y
       end
foo (generic function with 1 method)

julia> foo(1, 2)
took 9.5367431640625e-7 s
3
Run Code Online (Sandbox Code Playgroud)

然而,至少根据我的经验,这在惯用的 Julia 程序中出奇地很少出现。我会首先考虑您的特定问题是否可以通过具有普通高阶函数和特征的多重分派来更好地解决,这通常有助于更好的可组合性。