Skip to content

Commit

Permalink
Support one and oneunit with Missing
Browse files Browse the repository at this point in the history
  • Loading branch information
omus committed Nov 30, 2017
1 parent 96eb33a commit c94b05b
Show file tree
Hide file tree
Showing 2 changed files with 30 additions and 10 deletions.
13 changes: 8 additions & 5 deletions base/missing.jl
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ isless(::Missing, ::Any) = false
isless(::Any, ::Missing) = true

# Unary operators/functions
for f in (:(!), :(+), :(-), :(identity), :(zero),
for f in (:(!), :(+), :(-), :(identity), :(zero), :(one), :(oneunit),
:(abs), :(abs2), :(sign),
:(acos), :(acosh), :(asin), :(asinh), :(atan), :(atanh),
:(sin), :(sinh), :(cos), :(cosh), :(tan), :(tanh),
Expand All @@ -60,9 +60,12 @@ for f in (:(!), :(+), :(-), :(identity), :(zero),
@eval Math.$(f)(::Missing) = missing
end

zero(::Type{Union{T, Missing}}) where {T} = zero(T)
# To prevent StackOverflowError
zero(::Type{Any}) = throw(MethodError(zero, (Any,)))
for f in (:(Base.zero), :(Base.one), :(Base.oneunit))
@eval function $(f)(::Type{Union{T, Missing}}) where T
T === Any && throw(MethodError($f, (Any,))) # To prevent StackOverflowError
$f(T)
end
end

# Binary operators/functions
for f in (:(+), :(-), :(*), :(/), :(^),
Expand Down Expand Up @@ -112,4 +115,4 @@ function float(A::AbstractArray{Union{T, Missing}}) where {T}
U = typeof(float(zero(T)))
convert(AbstractArray{Union{U, Missing}}, A)
end
float(A::AbstractArray{Missing}) = A
float(A::AbstractArray{Missing}) = A
27 changes: 22 additions & 5 deletions test/missing.jl
Original file line number Diff line number Diff line change
Expand Up @@ -105,13 +105,20 @@ end
@test ismissing(missing * "a")
end

# Emulate a unitful type such as Dates.Minute
struct Unit
value::Int
end
Base.zero(::Type{Unit}) = Unit(0)
Base.one(::Type{Unit}) = 1

@testset "elementary functions" begin
elementary_functions = [abs, abs2, sign,
acos, acosh, asin, asinh, atan, atanh, sin, sinh,
conj, cos, cosh, tan, tanh,
exp, exp2, expm1, log, log10, log1p, log2,
exponent, sqrt, gamma, lgamma,
identity, zero,
identity, zero, one, oneunit,
iseven, isodd, ispow2,
isfinite, isinf, isnan, iszero,
isinteger, isreal, isempty, transpose, float]
Expand All @@ -121,11 +128,21 @@ end
@test ismissing(f(missing))
end

@test zero(Union{Int, Missing}) === 0
@test zero(Union{Float64, Missing}) === 0.0
for T in (Int, Float64)
@test zero(Union{T, Missing}) === T(0)
@test one(Union{T, Missing}) === T(1)
@test oneunit(Union{T, Missing}) === T(1)
end

for T in (Unit,)
@test zero(Union{T, Missing}) === T(0)
@test one(Union{T, Missing}) === 1
@test oneunit(Union{T, Missing}) === T(1)
end

@test_throws MethodError zero(Any)
@test_throws MethodError zero(String)
@test_throws MethodError zero(Union{String, Missing})
@test_throws MethodError one(Any)
@test_throws MethodError oneunit(Any)
end

@testset "rounding functions" begin
Expand Down

0 comments on commit c94b05b

Please sign in to comment.