From a236aff0023367a4511be1d8014bf77dc81640ee Mon Sep 17 00:00:00 2001 From: uribalb Date: Tue, 22 Sep 2020 07:04:34 +0100 Subject: [PATCH] handle keyword arguments in bounce macro addresses issue https://github.com/MikeInnes/Lazy.jl/issues/124 --- src/tail.jl | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/src/tail.jl b/src/tail.jl index 7042ac7..b5c400f 100644 --- a/src/tail.jl +++ b/src/tail.jl @@ -84,8 +84,8 @@ mutable struct Bounce f::Function end -function trampoline(f, args...) - val = f(args...) +function trampoline(f, args...; kwargs...) + val = f(args...; kwargs...) while isa(val, Bounce) val = val.f() end @@ -116,21 +116,24 @@ Tail recursion that doesn't blow the stack. For simple cases you probably want the much faster [`@rec`](@ref). """ macro bounce(def) - def = macroexpand(@__MODULE__, def) + def = macroexpand(@__MODULE__, prettify(def)) @assert isdef(def) @assert isexpr(def.args[1].args[1], Symbol) # TODO: handle f{T}() = ... f = namify(def) f_tramp = trampname(f) - args = def.args[1].args[2:end] def.args[1].args[1] = f_tramp - + @capture(def.args[1], ff_(args__; kwargs__)) || @capture(def.args[1], ff_(args__)) + isnothing(kwargs) && (kwargs = []) + calls = Symbol[] def.args[2] = tailcalls(ex -> (isexpr(ex, :call) && push!(calls, ex.args[1]); bounce(ex)), def.args[2]) + quote $([trampdef(call) for call in calls]...) $def - $f($(args...)) = Lazy.trampoline($f_tramp, $(args...)) + $f($(args...);$(kwargs...)) = trampoline($f_tramp, $(args...); $(kwargs...)) end |> esc + end