Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

add some methods for unary +, -, *, abs #245

Merged
merged 1 commit into from
Nov 30, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 18 additions & 0 deletions src/implementations/BigFloat.jl
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,10 @@ function operate_to!(output::BigFloat, ::typeof(+), a::BigFloat, b::BigFloat)
return output
end

operate_to!(out::BigFloat, ::typeof(+), a::BigFloat) = operate_to!(out, copy, a)

operate!(::typeof(+), a::BigFloat) = a

# -

promote_operation(::typeof(-), ::Vararg{Type{BigFloat},N}) where {N} = BigFloat
Expand All @@ -101,13 +105,23 @@ function operate!(::typeof(-), x::BigFloat)
return x
end

function operate_to!(o::BigFloat, ::typeof(-), x::BigFloat)
operate_to!(o, copy, x)
return operate!(-, o)
end

# Base.abs

function operate!(::typeof(Base.abs), x::BigFloat)
x.sign = abs(x.sign)
return x
end

function operate_to!(o::BigFloat, ::typeof(abs), x::BigFloat)
operate_to!(o, copy, x)
return operate!(abs, o)
end

# *

promote_operation(::typeof(*), ::Type{BigFloat}, ::Type{BigFloat}) = BigFloat
Expand All @@ -125,6 +139,10 @@ function operate_to!(output::BigFloat, ::typeof(*), a::BigFloat, b::BigFloat)
return output
end

operate_to!(out::BigFloat, ::typeof(*), a::BigFloat) = operate_to!(out, copy, a)

operate!(::typeof(*), a::BigFloat) = a

# Base.fma

function promote_operation(
Expand Down
26 changes: 26 additions & 0 deletions src/implementations/BigInt.jl
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,10 @@ function operate_to!(output::BigInt, ::typeof(+), a::BigInt, b::BigInt)
return Base.GMP.MPZ.add!(output, a, b)
end

operate_to!(out::BigInt, ::typeof(+), a::BigInt) = operate_to!(out, copy, a)

operate!(::typeof(+), a::BigInt) = a

# -

promote_operation(::typeof(-), ::Vararg{Type{BigInt},N}) where {N} = BigInt
Expand All @@ -52,6 +56,24 @@ function operate_to!(output::BigInt, ::typeof(-), a::BigInt, b::BigInt)
return Base.GMP.MPZ.sub!(output, a, b)
end

operate_to!(out::BigInt, ::typeof(-), a::BigInt) = Base.GMP.MPZ.neg!(out, a)

operate!(::typeof(-), a::BigInt) = operate_to!(a, -, a)

# abs

promote_operation(::typeof(abs), ::Type{BigInt}) = BigInt

function operate!(::typeof(abs), n::BigInt)
n.size = abs(n.size)
return n
end

function operate_to!(o::BigInt, ::typeof(abs), n::BigInt)
operate_to!(o, copy, n)
return operate!(abs, o)
end

# *

promote_operation(::typeof(*), ::Type{BigInt}, ::Type{BigInt}) = BigInt
Expand All @@ -60,6 +82,10 @@ function operate_to!(output::BigInt, ::typeof(*), a::BigInt, b::BigInt)
return Base.GMP.MPZ.mul!(output, a, b)
end

operate_to!(out::BigInt, ::typeof(*), a::BigInt) = operate_to!(out, copy, a)

operate!(::typeof(*), a::BigInt) = a

promote_operation(::typeof(div), ::Type{BigInt}, ::Type{BigInt}) = BigInt

function operate_to!(output::BigInt, ::typeof(div), a::BigInt, b::BigInt)
Expand Down
38 changes: 38 additions & 0 deletions src/implementations/Rational.jl
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,38 @@ function operate_to!(output::Rational, ::typeof(+), x::Rational, y::Rational)
return output
end

function operate_to!(out::Q, ::typeof(+), x::Q) where {Q<:Rational}
return operate_to!(out, copy, x)
end

operate!(::typeof(+), x::Rational) = x

function operate_to!(out::Q, ::typeof(-), x::Q) where {Q<:Rational}
operate_to!(out.num, -, x.num)
operate_to!(out.den, copy, x.den)
return out
end

function operate!(::typeof(-), x::Rational)
operate!(-, x.num)
return x
end

# abs

promote_operation(::typeof(abs), ::Type{Q}) where {Q<:Rational} = Q

function operate!(::typeof(abs), x::Rational)
operate!(abs, x.num)
return x
end

function operate_to!(o::Q, ::typeof(abs), x::Q) where {Q<:Rational}
operate_to!(o.num, abs, x.num)
operate_to!(o.den, copy, x.den)
return o
end

# *

function promote_operation(
Expand Down Expand Up @@ -174,6 +206,12 @@ function operate_to!(output::Rational, ::typeof(*), x::Rational, y::Rational)
)
end

function operate_to!(out::Q, ::typeof(*), x::Q) where {Q<:Rational}
return operate_to!(out, copy, x)
end

operate!(::typeof(*), x::Rational) = x

# gcd

function promote_operation(
Expand Down
23 changes: 23 additions & 0 deletions test/interface.jl
Original file line number Diff line number Diff line change
Expand Up @@ -155,3 +155,26 @@ end
y = MA.operate!!(MA.add_mul, z, 2.4, LinearAlgebra.Diagonal(1:2))
@test y == LinearAlgebra.Diagonal(2.4 * (1:2))
end

@testset "unary op(::$T)" for T in (
Float64,
BigFloat,
Int,
BigInt,
Rational{Int},
Rational{BigInt},
)
@test MA.operate!!(+, T(7)) == 7
@test MA.operate!!(*, T(7)) == 7
@test MA.operate!!(-, T(7)) == -7

@test MA.operate_to!!(T(6), +, T(7)) == 7
@test MA.operate_to!!(T(6), *, T(7)) == 7
@test MA.operate_to!!(T(6), -, T(7)) == -7

@test MA.operate!!(abs, T(7)) == 7
@test MA.operate!!(abs, T(-7)) == 7

@test MA.operate_to!!(T(6), abs, T(7)) == 7
@test MA.operate_to!!(T(6), abs, T(-7)) == 7
end