The point of the hypot
function is to avoid underflow and overflow, however the implementation of the vararg method introduced with PR #25571 defeats this purpose:
julia> hypot(1e200, 0, 0)
Inf
julia> hypot(1e-300, 0, 0)
0.0
Instead in Julia 0.6 it gives the correct result:
ulia> hypot(1e200, 0, 0)
1.0e200
julia> hypot(1e-300, 0, 0)
1.0e-300
Edit: I've just seen this was already pointed out in https://github.com/JuliaLang/julia/pull/25571#discussion_r162442508
Maybe just define:
hypot(x::Number...) = vecnorm(x)
@stevengj I think the problem is that vecnorm
is part of LinAlg.
One alternative would be
hypot(x,y,z...) = hypot(hypot(x,y), z...)
That would be a performance trap, in that it would be much slower than expected.
We can also just reimplement the relevant part of vecnorm: it doesn’t take more than a few lines to do the right thing.
The following cases give even worse failures due to integer wraparound:
julia> i = typemax(Int)
9223372036854775807
julia> hypot(i,i,i) # the result is √3 !!
1.7320508075688772
julia> i*√3
1.5975348984942514e19
julia> hypot(10^17, 10^17, 10^17) # 3*abs2(10^17) is negative!
ERROR: DomainError with -6.437707461859213e18:
There should definitely be a test for the i = typemax(Int)
case in any solution PR.
Most helpful comment