当计算幅度<1且幅度> 1时的精度损失

时间:2014-05-31 00:37:18

标签: c++ string boost gmp arbitrary-precision

我正在测试字符串构造gmp_float

此代码

#include <boost/multiprecision/number.hpp>
#include <boost/multiprecision/gmp.hpp>
#include <iostream>

using namespace boost::multiprecision;

typedef number<gmp_float<15>> mp_type;

int main()
{
    mp_type total("1.01");
    cout << total.str(0) << endl;
    mp_type first_addition(".01");
    cout << first_addition.str(0) << endl;
    total += first_addition;
    cout << total.str(0) << endl;
}

打印

1.01
0.01
1.01999999999999999998

为什么呢?我运行了更多的测试,在这种特殊情况下,只要一个数字的大小> 0且<1而另一个的数量大于1,操作是什么并不重要。

从上面的链接

  

无法将此类型的对象往返于字符串中并从字符串中返回完全相同的值。这似乎是GMP的限制。

是否还有其他准确性丢失的区域?

2 个答案:

答案 0 :(得分:2)

GMP中的

mpf_t二进制浮点数。 0.01不能完全表示为任何有限精度的二进制浮点数。

更改0.01的{​​{1}}和0.125的{​​{1}}会使格式化的输出看起来很好。这是因为1.011.125可以完全表示为具有至少8位有效数字的二进制浮点数。

答案 1 :(得分:2)

Boost Multiprecision也有十进制浮点数:

查看 Live On Coliru 打印:

clang++ -std=c++11 -Os -Wall -pedantic main.cpp && ./a.out
1.01
0.01
1.02

#include <boost/multiprecision/cpp_dec_float.hpp>
#include <iostream>

using namespace boost::multiprecision;
using std::cout;
using std::endl;

typedef cpp_dec_float_50 mp_type;

int main()
{
    mp_type total("1.01");
    cout << total.str(0)          << endl;

    mp_type first_addition(".01");
    cout << first_addition.str(0) << endl;

    total += first_addition;
    cout << total.str(0)          << endl;
}