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

[SR-8409] Decimal initialized with Double loses precision #3658

swift-ci opened this issue Jul 30, 2018 · 3 comments

[SR-8409] Decimal initialized with Double loses precision #3658

swift-ci opened this issue Jul 30, 2018 · 3 comments


Copy link

Previous ID SR-8409
Radar None
Original Reporter TomasLinhart (JIRA User)
Type Bug
Additional Detail from JIRA
Votes 0
Component/s Foundation
Labels Bug
Assignee None
Priority Medium

md5: 87fa6caf176bfbf5ed96bbc10110c73b

is duplicated by:

  • SR-11514 Decimal.init(_ value: Double) sometimes yields incorrect value

Issue Description:

Decimal precision is a bit strange for a number 456.789. When you initialize Double with 456.789 it holds the number so it is representable, but if you try to convert it to a decimal with Decimal(456.789) it results in 456.7889999999998976 but if you use Decimal(string: "456.789")! it results in a correct decimal with a value 456.789.

I tried also Objective-C, and it works correctly there:

NSDecimalNumber *number = [[NSDecimalNumber alloc] initWithDouble:456.789];
NSLog(@"Number: %f", number.doubleValue);
Copy link

cc @stephentyrone

Copy link

This is mostly expected. `456.789 as Double` has the exact value 456.788999999999987267074175179004669189453125, which is not exactly representable as `Decimal`, so it gets rounded to a representable `Decimal` value.

That second rounding appears to be not quite perfect (that's a Foundation bug), but even if Foundation were rounding correctly, the result would not be 456.789. It would be something like 456.78899999999998726707417517900466919 instead.

Copy link

spevans commented Jan 20, 2019

I wonder if a better solution would be to use the .description property of Double:

public init(_ value: Double) {
    self = Decimal(string: value.description) ?? Decimal.nan

and Decimal.description:

internal var doubleValue: Double {
    return Double(self.description) ?? Double.nan

Whilst there will be a conversion cost going via a String, it may provide less surprising values overall.

@swift-ci swift-ci transferred this issue from apple/swift-issues Apr 25, 2022
@shahmishal shahmishal transferred this issue from apple/swift May 5, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
None yet

No branches or pull requests

4 participants