JuliaMath / GSL.jl

Julia interface to the GNU Scientific Library (GSL)

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Stack overflow from hypergeometric 1F1

yha opened this issue · comments

commented

May be an upstream bug, since the stack overflow seems to happen inside the C function

using GSL
set_error_handler_off()
hypergeom(1,NaN,-1)
StackOverflowError:
sf_hyperg_1F1 at gsl_sf_hyperg_h.jl:116 [inlined]
hypergeom(::Int64, ::Float64, ::Int64) at manual_wrappers.jl:252
top-level scope at none:0

Running without the error handler disabled I get:

julia> sf_hyperg_1F1_e(1.0,NaN,-1.0)
┌ Warning: GSL Error 18 (roundoff error): x too large to extract fraction part at gamma.c:1249
└ @ GSL.C ~/.julia/dev/GSL/src/error_handling.jl:23
ERROR: GSL Error 18 (roundoff error): x too large to extract fraction part at gamma.c:1249
Stacktrace:
 [1] custom_error_handler(::String, ::String, ::Int32, ::Int32) at /Users/simon/.julia/dev/GSL/src/error_handling.jl:42
 [2] custom_error_handler(::Ptr{UInt8}, ::Ptr{UInt8}, ::Int32, ::Int32) at /Users/simon/.julia/dev/GSL/src/error_handling.jl:9
 [3] sf_hyperg_1F1_e at /Users/simon/.julia/dev/GSL/src/gen/direct_wrappers/gsl_sf_hyperg_h.jl:86 [inlined]
 [4] sf_hyperg_1F1_e(::Float64, ::Float64, ::Float64) at /Users/simon/.julia/dev/GSL/src/gen/heuristic_wrappers.jl:3374
 [5] top-level scope at none:0

So I'm guessing this is an upstream bug?

From what I understand, if you disable the error handler you're supposed to use the checked versions (hypergeom_e in this case), but I still see the error there.

Judging by the number of bug reports on Savannah, it seems like the GSL implementations of hypergeometric functions need some work. Until then, I would probably recommend using the implementations available in SciPy instead.

Also, based on the commit history, GSL seems to effectively be down to one maintainer, so I wouldn't expect a fix any time soon.

commented

The SciPy implementation also has its fair share of bug reports, and there are regions where GSL does better, such as M(1,201,-0.01)=exp(-0.01)*M(200,201,0.01), which should be slightly less than 1:

julia> GSL.hypergeom(1.0,201.0,-0.01)
0.9999502512190305
julia> @pyimport scipy.special as special
julia> special.hyp1f1(1.0,201.0,-0.01)
-9.228474834209045e26

Also, GSL has error estimates, which scipy doesn't seem to have, and of course is much faster than calling out to python through PyCall.
I'll open a PR to add NaN checks on the Julia side.

Fair enough. Properly evaluating these things for any argument seems hard!

On a side note, the GSL error estimates are in some cases completely off: https://savannah.gnu.org/bugs/?54998