ForwardDiff.jl icon indicating copy to clipboard operation
ForwardDiff.jl copied to clipboard

StackOverflowError when differentiating a simple scalar function from SpecialFunctions.jl

Open Matematija opened this issue 4 years ago • 2 comments

Here is the MWE:

using ForwardDiff
using SpecialFunctions

log_i0(z::Number) = besseli(0,z) |> log
ForwardDiff.jacobian(x -> log_i0.(x), [1.1, 2.2, 3.3])

REPL output:

ERROR: LoadError: StackOverflowError:
Stacktrace:
 [1] besselix(nu::Int64, x::ForwardDiff.Dual{ForwardDiff.Tag{var"#8#9", Float64}, Float64, 3}) (repeats 79984 times)
   @ SpecialFunctions ~/.julia/packages/SpecialFunctions/NBIqR/src/bessel.jl:583
in expression starting at (...)

Interestingly,

ForwardDiff.jacobian(x -> log.(besseli.(0, x)), [1.1, 2.2, 3.3])

works great. Am I missing something super-obvious here? (My honest apologies if I am.)

Environment:

  • Julia Version 1.6.2
  • SpecialFunctions v1.8.1
  • ForwardDiff v0.10.23

Matematija avatar Nov 29 '21 03:11 Matematija

I think the stack overflow is telling you it's not supported.

The method is (I presume) meant to send besseli(0, 3) to besseli(0, 3.0), but instead catches dual numbers for which there is no more specific method:

https://github.com/JuliaMath/SpecialFunctions.jl/blob/master/src/bessel.jl#L583

There are methods accepting Dual only for certain Bessel functions:

https://github.com/JuliaDiff/DiffRules.jl/blob/master/src/rules.jl#L143-L150

mcabbott avatar Jan 13 '22 20:01 mcabbott

Okay, that makes sense, thank you. I am still confused as to why does the second example work without a problem then.

Matematija avatar Jan 15 '22 20:01 Matematija