Skip to content

Commit c10c451

Browse files
Make constructors for basic number types inferable (#37213)
1 parent f8a73da commit c10c451

File tree

7 files changed

+31
-17
lines changed

7 files changed

+31
-17
lines changed

base/float.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ A not-a-number value of type [`Float64`](@ref).
4848
NaN, NaN64
4949

5050
## conversions to floating-point ##
51-
Float16(x::Integer) = convert(Float16, convert(Float32, x))
51+
Float16(x::Integer) = convert(Float16, convert(Float32, x)::Float32)
5252
for t in (Int8, Int16, Int32, Int64, Int128, UInt8, UInt16, UInt32, UInt64, UInt128)
5353
@eval promote_rule(::Type{Float16}, ::Type{$t}) = Float16
5454
end

base/irrationals.jl

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -42,8 +42,8 @@ promote_rule(::Type{<:AbstractIrrational}, ::Type{<:AbstractIrrational}) = Float
4242
promote_rule(::Type{<:AbstractIrrational}, ::Type{T}) where {T<:Real} = promote_type(Float64, T)
4343
promote_rule(::Type{S}, ::Type{T}) where {S<:AbstractIrrational,T<:Number} = promote_type(promote_type(S, real(T)), T)
4444

45-
AbstractFloat(x::AbstractIrrational) = Float64(x)
46-
Float16(x::AbstractIrrational) = Float16(Float32(x))
45+
AbstractFloat(x::AbstractIrrational) = Float64(x)::Float64
46+
Float16(x::AbstractIrrational) = Float16(Float32(x)::Float32)
4747
Complex{T}(x::AbstractIrrational) where {T<:Real} = Complex{T}(T(x))
4848

4949
@pure function Rational{T}(x::AbstractIrrational) where T<:Integer
@@ -64,7 +64,7 @@ Rational{BigInt}(x::AbstractIrrational) = throw(ArgumentError("Cannot convert an
6464

6565
@pure function (t::Type{T})(x::AbstractIrrational, r::RoundingMode) where T<:Union{Float32,Float64}
6666
setprecision(BigFloat, 256) do
67-
T(BigFloat(x), r)
67+
T(BigFloat(x)::BigFloat, r)
6868
end
6969
end
7070

base/mpfr.jl

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -224,8 +224,10 @@ function BigFloat(x::BigInt, r::MPFRRoundingMode=ROUNDING_MODE[]; precision::Int
224224
return z
225225
end
226226

227-
BigFloat(x::Integer, r::MPFRRoundingMode=ROUNDING_MODE[]; precision::Integer=DEFAULT_PRECISION[]) =
228-
BigFloat(BigInt(x), r; precision=precision)
227+
BigFloat(x::Integer; precision::Integer=DEFAULT_PRECISION[]) =
228+
BigFloat(BigInt(x)::BigInt, ROUNDING_MODE[]; precision=precision)
229+
BigFloat(x::Integer, r::MPFRRoundingMode; precision::Integer=DEFAULT_PRECISION[]) =
230+
BigFloat(BigInt(x)::BigInt, r; precision=precision)
229231

230232
BigFloat(x::Union{Bool,Int8,Int16,Int32}, r::MPFRRoundingMode=ROUNDING_MODE[]; precision::Integer=DEFAULT_PRECISION[]) =
231233
BigFloat(convert(Clong, x), r; precision=precision)
@@ -238,7 +240,7 @@ BigFloat(x::Union{Float16,Float32}, r::MPFRRoundingMode=ROUNDING_MODE[]; precisi
238240
function BigFloat(x::Rational, r::MPFRRoundingMode=ROUNDING_MODE[]; precision::Integer=DEFAULT_PRECISION[])
239241
setprecision(BigFloat, precision) do
240242
setrounding_raw(BigFloat, r) do
241-
BigFloat(numerator(x)) / BigFloat(denominator(x))
243+
BigFloat(numerator(x))::BigFloat / BigFloat(denominator(x))::BigFloat
242244
end
243245
end
244246
end
@@ -259,7 +261,7 @@ AbstractFloat(x::BigInt) = BigFloat(x)
259261
float(::Type{BigInt}) = BigFloat
260262

261263
BigFloat(x::Real, r::RoundingMode; precision::Integer=DEFAULT_PRECISION[]) =
262-
BigFloat(x, convert(MPFRRoundingMode, r); precision=precision)
264+
BigFloat(x, convert(MPFRRoundingMode, r); precision=precision)::BigFloat
263265
BigFloat(x::AbstractString, r::RoundingMode; precision::Integer=DEFAULT_PRECISION[]) =
264266
BigFloat(x, convert(MPFRRoundingMode, r); precision=precision)
265267

base/rational.jl

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -106,13 +106,13 @@ Rational(x::Rational) = x
106106

107107
Bool(x::Rational) = x==0 ? false : x==1 ? true :
108108
throw(InexactError(:Bool, Bool, x)) # to resolve ambiguity
109-
(::Type{T})(x::Rational) where {T<:Integer} = (isinteger(x) ? convert(T, x.num) :
109+
(::Type{T})(x::Rational) where {T<:Integer} = (isinteger(x) ? convert(T, x.num)::T :
110110
throw(InexactError(nameof(T), T, x)))
111111

112-
AbstractFloat(x::Rational) = float(x.num)/float(x.den)
112+
AbstractFloat(x::Rational) = (float(x.num)/float(x.den))::AbstractFloat
113113
function (::Type{T})(x::Rational{S}) where T<:AbstractFloat where S
114114
P = promote_type(T,S)
115-
convert(T, convert(P,x.num)/convert(P,x.den))
115+
convert(T, convert(P,x.num)/convert(P,x.den))::T
116116
end
117117

118118
function Rational{T}(x::AbstractFloat) where T<:Integer

base/rounding.jl

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -197,19 +197,19 @@ end
197197
# Assumes conversion is performed by rounding to nearest value.
198198

199199
# To avoid ambiguous dispatch with methods in mpfr.jl:
200-
(::Type{T})(x::Real, r::RoundingMode) where {T<:AbstractFloat} = _convert_rounding(T,x,r)
200+
(::Type{T})(x::Real, r::RoundingMode) where {T<:AbstractFloat} = _convert_rounding(T,x,r)::T
201201

202-
_convert_rounding(::Type{T}, x::Real, r::RoundingMode{:Nearest}) where {T<:AbstractFloat} = convert(T,x)
202+
_convert_rounding(::Type{T}, x::Real, r::RoundingMode{:Nearest}) where {T<:AbstractFloat} = convert(T,x)::T
203203
function _convert_rounding(::Type{T}, x::Real, r::RoundingMode{:Down}) where T<:AbstractFloat
204-
y = convert(T,x)
204+
y = convert(T,x)::T
205205
y > x ? prevfloat(y) : y
206206
end
207207
function _convert_rounding(::Type{T}, x::Real, r::RoundingMode{:Up}) where T<:AbstractFloat
208-
y = convert(T,x)
208+
y = convert(T,x)::T
209209
y < x ? nextfloat(y) : y
210210
end
211211
function _convert_rounding(::Type{T}, x::Real, r::RoundingMode{:ToZero}) where T<:AbstractFloat
212-
y = convert(T,x)
212+
y = convert(T,x)::T
213213
if x > 0.0
214214
y > x ? prevfloat(y) : y
215215
else

test/numbers.jl

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2692,3 +2692,15 @@ end
26922692
end
26932693
end
26942694
end
2695+
2696+
@testset "constructor inferability for $T" for T in [AbstractFloat, #=BigFloat,=# Float16,
2697+
Float32, Float64, Integer, Bool, Signed, BigInt, Int128, Int16, Int32, Int64, Int8,
2698+
Unsigned, UInt128, UInt16, UInt32, UInt64, UInt8]
2699+
@test all(R -> R<:T, Base.return_types(T))
2700+
end
2701+
@testset "constructor inferability for BigFloat" begin
2702+
T = BigFloat
2703+
@test_broken all(R -> R<:T, Base.return_types(T))
2704+
@test all(m -> m.file == Symbol("deprecated.jl"),
2705+
collect(methods(T))[findall(R -> !(R<:T), Base.return_types(T))])
2706+
end

test/testhelpers/Furlongs.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ struct Furlong{p,T<:Number} <: Number
1414
end
1515
Furlong(x::T) where {T<:Number} = Furlong{1,T}(x)
1616
Furlong(x::Furlong) = x
17-
(::Type{T})(x::Furlong) where {T<:Number} = T(x.val)
17+
(::Type{T})(x::Furlong) where {T<:Number} = T(x.val)::T
1818
Furlong{p}(v::Number) where {p} = Furlong{p,typeof(v)}(v)
1919
Furlong{p}(x::Furlong{q}) where {p,q} = (@assert(p==q); Furlong{p,typeof(x.val)}(x.val))
2020
Furlong{p,T}(x::Furlong{q}) where {T,p,q} = (@assert(p==q); Furlong{p,T}(T(x.val)))

0 commit comments

Comments
 (0)