Skip to content
New issue

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

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

Already on GitHub? # to your account

package modernization including better type stability #42

Closed
wants to merge 2 commits into from

Conversation

ExpandingMan
Copy link
Contributor

Seemed like this package needed a bit of an overhaul as it appears to be basically the default arbitrary precision decimal arithmetic package. It still needs a ton of work, but I think this is a good start. The most significant improvement is in type stability as the fields of Decimal are now concrete types.

At first I was going to make Decimal parametric with a type parameter for the exponent, but ultimately I decided that the benefit if this was pretty dubious, so I set the exponent to simply be an Int. Because of this, these changes should be pretty much non-breaking.

@coveralls
Copy link

coveralls commented Nov 22, 2019

Pull Request Test Coverage Report for Build 113

  • 12 of 15 (80.0%) changed or added relevant lines in 4 files are covered.
  • No unchanged relevant lines lost coverage.
  • Overall coverage decreased (-2.6%) to 92.638%

Changes Missing Coverage Covered Lines Changed/Added Lines %
src/decimal.jl 6 9 66.67%
Totals Coverage Status
Change from base Build 111: -2.6%
Covered Lines: 302
Relevant Lines: 326

💛 - Coveralls

@codecov-io
Copy link

codecov-io commented Nov 22, 2019

Codecov Report

Attention: Patch coverage is 80.00000% with 3 lines in your changes missing coverage. Please review.

Project coverage is 92.72%. Comparing base (b7f569e) to head (b684caf).
Report is 27 commits behind head on master.

Files with missing lines Patch % Lines
src/decimal.jl 66.66% 3 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##           master      #42      +/-   ##
==========================================
- Coverage   95.28%   92.72%   -2.56%     
==========================================
  Files           6        6              
  Lines         106      110       +4     
==========================================
+ Hits          101      102       +1     
- Misses          5        8       +3     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

Copy link
Contributor

@iamed2 iamed2 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks fine from my perspective (LibPQ)

end
# Numerical value: (-1)^s * c * 10^q
struct Decimal <: AbstractFloat
s::Bool # sign can be 0 (+) or 1 (-)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why don't we roll this into c ?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was actually wondering the same thing, I just didn't bother to change it. I only spent about half an hour on this PR, mostly for the sake of type stability. If the separate sign bit really is unnecessary, suggest somebody make another PR later to change it.

Copy link
Contributor

@hurak hurak Nov 25, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let me add another input. It appears that there is no standard for arbitrary precision decimal arithmetics (there is only IEEE 754-2008 standard introducing 32, 64, and 64-bit precisions - decimal32, decimal64 and decimal128, respectively, and these are already implemented in Julia package called DecFP). Since Decimals.jl package aims at implementing arbitrary precision decimal arithmetics, it may enjoy freedom from official standards. Good. Nonetheless, there is General Decimal Arithmetic Specification by IBM, which sort of extends the IEEE 754-2008 towards arbitrary precision. Perhaps it does not have the same status of official IEEE standards, but apparently, the now built-in Python package decimal is implementing it. I tried to sketch these relationships at the bottom of the front page (README.md).

Now, although I was not involved in the Decimals.jl package development (I only joined very recently) my perception of the package is that it might aim at the same goal as the Python's decimal. If this goal is shared, I think it would be wise to keep the arithmetic model as close as possible.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't necessarily dispute any of that, but this PR was just a quick update mostly to get rid of the unnecessary type instability. This package clearly could use a lot of work, I'd like it if we could merge this to get in what improvement we can for now and work can continue.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should move this discusion into #44

@oxinabox oxinabox mentioned this pull request Nov 25, 2019
end
c, q = parameters(('.' in str) ? split(str, '.') : str)
normalize(Decimal((str[1] == '-') ? 1 : 0, c, q))
normalize(Decimal((str[1] == '-'), c, q))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
normalize(Decimal((str[1] == '-'), c, q))
normalize(Decimal(str[1] == '-', c, q))

@@ -60,8 +62,10 @@ function Base.print(io::IO, x::Decimal)
end

# Zero/one value
Base.zero(::Type{Decimal}) = Decimal(0,0,0)
Base.one(::Type{Decimal}) = Decimal(0,1,0)
Base.zero(::Type{Decimal}) = Decimal(false,0,0)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
Base.zero(::Type{Decimal}) = Decimal(false,0,0)
Base.zero(::Type{Decimal}) = Decimal(false, 0, 0)

Base.zero(::Type{Decimal}) = Decimal(0,0,0)
Base.one(::Type{Decimal}) = Decimal(0,1,0)
Base.zero(::Type{Decimal}) = Decimal(false,0,0)
Base.one(::Type{Decimal}) = Decimal(false,1,0)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
Base.one(::Type{Decimal}) = Decimal(false,1,0)
Base.one(::Type{Decimal}) = Decimal(false, 1, 0)

Base.signbit(x::Decimal) = x.s != 0
Base.signbit(x::Decimal) = x.s

Base.show(io::IO, x::Decimal) = write(io, "decimal(\""*string(x)*"\")")
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
Base.show(io::IO, x::Decimal) = write(io, "decimal(\""*string(x)*"\")")
Base.show(io::IO, x::Decimal) = write(io, "decimal(\"$x\")")


# Multiplication
function *(x::Decimal, y::Decimal)
function Base.:(*)(x::Decimal, y::Decimal)
s = (x.s == y.s) ? 0 : 1
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
s = (x.s == y.s) ? 0 : 1
s = x.s != y.s

@@ -17,25 +17,25 @@ function +(x::Decimal, y::Decimal)
end

# Negation
-(x::Decimal) = Decimal((x.s == 1) ? 0 : 1, x.c, x.q)
Base.:(-)(x::Decimal) = Decimal((x.s == 1) ? 0 : 1, x.c, x.q)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
Base.:(-)(x::Decimal) = Decimal((x.s == 1) ? 0 : 1, x.c, x.q)
Base.:(-)(x::Decimal) = Decimal(!x.s, x.c, x.q)

@barucden barucden mentioned this pull request Oct 15, 2024
@barucden barucden closed this in #66 Oct 15, 2024
# for free to join this conversation on GitHub. Already have an account? # to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

7 participants