如何在C ++中精确显示double的十进制数字?

时间:2011-07-11 08:20:02

标签: c++ algorithm numbers double

  

问题
  给定两个整数a,b,a<湾显示其十进制扩展。您将打印给定的整数商的十进制扩展,就像扩展终止时一样停止,或者就像重复模式第一次重复一样。如果存在重复模式,您将说明重复模式中有多少位数。

     

示例输入
  3 7
  345 800
  112 990
  53 122

     

示例输出
  0.428751
  最后6位数字永远重复   0.43125
  这种扩张终止了   .113
  最后两位数字永远重复   .4344262295081967213114754098360655737704918032786885245901639
  最后60位数字永远重复。

注意:此问题来自ProgFest编程竞赛。

如果我们应用这三个定理,这个问题的算法并不困难: enter image description here

然而,我面临的问题是使用定理1中给出的递归公式计算alpha时的舍入。显示函数定义如下:

void displayFraction( int n, int d, int length ) {
    std::cout << ".";
    double alpha = static_cast<double>( n ) / d;
    for( int i = 1; i <= length; ++i ) {
        int c = std::floor( 10.0 * alpha );
        alpha = 10.0 * alpha - c;
        std::cout << c;
    }
}

我的输出是:

.4344 2622 9508 1967 3732 7807 5683 6291 4025 7835 3881 8359 3750 0000 0000 0

问题输出是:

.4344 2622 9508 1967 2131 1475 4098 3606 5573 7704 9180 3278 6885 2459 0163 9

正如您所看到的,直到第16位才是正确的。所以我的问题是,在这种特殊情况下执行计算时如何防止截断数字?有什么想法吗?

3 个答案:

答案 0 :(得分:4)

问题是double没有无限的精度,而是只能管理大约16个十进制数字。因为输入double中基本缺乏信息,所以你遇到麻烦(有趣,那个!)。

你需要找到一种解决问题的方法,当你从中得到更多的数字时,这个问题会越来越接近答案。这意味着你需要更多地思考定理3,并且还要根据有理数而不是浮点来编写代码。

答案 1 :(得分:2)

使用像gmp这样的bignum库。只有这么多信息可以打包成双人。

答案 2 :(得分:2)

我认为你想要一个任意精度库

gnu MP bignum之类的东西,虽然其他风格是available