Skip to content

Commit f6e55a7

Browse files
authored
Merge pull request #22644 from angusmoore/anm/ranges-32bit-#22613
Handle 32 bit architecture when creating float ranges (#22613)
2 parents 5eb4112 + 7f163ba commit f6e55a7

File tree

5 files changed

+27
-11
lines changed

5 files changed

+27
-11
lines changed

base/docs/helpdb/Base.jl

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1143,7 +1143,15 @@ bswap
11431143
11441144
The largest integer losslessly representable by the given floating-point DataType `T`.
11451145
"""
1146-
maxintfloat
1146+
maxintfloat(T)
1147+
1148+
"""
1149+
maxintfloat(T, S)
1150+
1151+
The largest integer losslessly representable by the given floating-point DataType `T` that
1152+
also does not exceed the maximum integer representable by the integer DataType `S`.
1153+
"""
1154+
maxintfloat(T, S)
11471155

11481156
"""
11491157
delete!(collection, key)

base/floatfuncs.jl

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ maxintfloat(::Type{Float64}) = 9007199254740992.
2020
maxintfloat(::Type{Float32}) = Float32(16777216.)
2121
maxintfloat(::Type{Float16}) = Float16(2048f0)
2222
maxintfloat(x::T) where {T<:AbstractFloat} = maxintfloat(T)
23+
maxintfloat(::Type{S}, ::Type{T}) where {S<:AbstractFloat, T<:Integer} = min(maxintfloat(S), S(typemax(T)))
2324
maxintfloat() = maxintfloat(Float64)
2425

2526
isinteger(x::AbstractFloat) = (x - trunc(x) == 0)

base/twiceprecision.jl

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -106,7 +106,7 @@ end
106106

107107
function floatrange(a::AbstractFloat, st::AbstractFloat, len::Real, divisor::AbstractFloat)
108108
T = promote_type(typeof(a), typeof(st), typeof(divisor))
109-
m = maxintfloat(T)
109+
m = maxintfloat(T, Int)
110110
if abs(a) <= m && abs(st) <= m && abs(divisor) <= m
111111
ia, ist, idivisor = round(Int, a), round(Int, st), round(Int, divisor)
112112
if ia == a && ist == st && idivisor == divisor
@@ -131,7 +131,7 @@ function colon(start::T, step::T, stop::T) where T<:Union{Float16,Float32,Float6
131131
if start_d != 0 && stop_d != 0 &&
132132
T(start_n/start_d) == start && T(stop_n/stop_d) == stop
133133
den = lcm(start_d, step_d) # use same denominator for start and step
134-
m = maxintfloat(T)
134+
m = maxintfloat(T, Int)
135135
if den != 0 && abs(start*den) <= m && abs(step*den) <= m && # will round succeed?
136136
rem(den, start_d) == 0 && rem(den, step_d) == 0 # check lcm overflow
137137
start_n = round(Int, start*den)
@@ -167,7 +167,7 @@ function range(a::T, st::T, len::Integer) where T<:Union{Float16,Float32,Float64
167167
if start_d != 0 && step_d != 0 &&
168168
T(start_n/start_d) == a && T(step_n/step_d) == st
169169
den = lcm(start_d, step_d)
170-
m = maxintfloat(T)
170+
m = maxintfloat(T, Int)
171171
if abs(den*a) <= m && abs(den*st) <= m &&
172172
rem(den, start_d) == 0 && rem(den, step_d) == 0
173173
start_n = round(Int, den*a)
@@ -257,7 +257,7 @@ function _convertSRL(::Type{StepRangeLen{T,R,S}}, r::Range{U}) where {T,R,S,U}
257257
if start_d != 0 && step_d != 0 &&
258258
U(start_n/start_d) == f && U(step_n/step_d) == s
259259
den = lcm(start_d, step_d)
260-
m = maxintfloat(T)
260+
m = maxintfloat(T, Int)
261261
if den != 0 && abs(f*den) <= m && abs(s*den) <= m &&
262262
rem(den, start_d) == 0 && rem(den, step_d) == 0
263263
start_n = round(Int, f*den)
@@ -326,7 +326,7 @@ function linspace(start::T, stop::T, len::Integer) where T<:Union{Float16,Float3
326326
stop_n, stop_d = rat(stop)
327327
if start_d != 0 && stop_d != 0
328328
den = lcm(start_d, stop_d)
329-
m = maxintfloat(T)
329+
m = maxintfloat(T, Int)
330330
if den != 0 && abs(den*start) <= m && abs(den*stop) <= m
331331
start_n = round(Int, den*start)
332332
stop_n = round(Int, den*stop)

test/floatfuncs.jl

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,11 +14,15 @@ end
1414

1515
# maxintfloat
1616

17-
@test maxintfloat(Float16) == Float16(2048f0)
17+
@test maxintfloat(Float16) === Float16(2048f0)
1818
for elty in (Float16,Float32,Float64)
19-
@test maxintfloat(rand(elty)) == maxintfloat(elty)
19+
@test maxintfloat(rand(elty)) === maxintfloat(elty)
2020
end
21-
@test maxintfloat() == maxintfloat(Float64)
21+
@test maxintfloat() === maxintfloat(Float64)
22+
@test maxintfloat(Float64, Int32) === 2147483647.0
23+
@test maxintfloat(Float32, Int32) === maxintfloat(Float32)
24+
@test maxintfloat(Float64, Int16) === 32767.0
25+
@test maxintfloat(Float64, Int64) === maxintfloat(Float64)
2226

2327
# isinteger
2428
for elty in (Float16,Float32,Float64)

test/ranges.jl

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -356,15 +356,18 @@ for T = (Float32, Float64,), i = 1:2^15, n = 1:5
356356
# FIXME: these fail some small portion of the time
357357
@test_skip start == first(r)
358358
@test_skip stop == last(r)
359-
# FIXME: linspace construction fails on 32-bit
360-
Sys.WORD_SIZE == 64 || continue
361359
l = linspace(start,stop,n)
362360
@test n == length(l)
363361
# FIXME: these fail some small portion of the time
364362
@test_skip start == first(l)
365363
@test_skip stop == last(l)
366364
end
367365

366+
# Inexact errors on 32 bit architectures. #22613
367+
@test first(linspace(log(0.2), log(10.0), 10)) == log(0.2)
368+
@test last(linspace(log(0.2), log(10.0), 10)) == log(10.0)
369+
@test length(Base.floatrange(-3e9, 1.0, 1, 1.0)) == 1
370+
368371
# linspace & ranges with very small endpoints
369372
for T = (Float32, Float64)
370373
z = zero(T)

0 commit comments

Comments
 (0)