c++ - 用C++计算小双数时出错

标签 c++ qt double

我正在使用 C++/Qt 对小 double 进行计算,但发生了一些奇怪的事情。在以下代码中,t_prob 的值应为 1.62457e-12,但实际为 3.24907e-12(如 2 * 1.62457e-12)。

同时,我添加了a,b,c,d的控件,结果是正确的。

你能给我一些关于这个问题的建议吗?提前致谢。

#include <QDebug>
#include <QtMath>

#define PI 3.1415926536

double tprob(qint64 n, double x);

int main(int argc, char *argv[])
{
    double a = 1.0;
    double b = 0.00000000000162448;
    double c = a - b;
    double d = 1.0 - c;

    qDebug() << "a:" << a;
    qDebug() << "b:" << b;
    qDebug() << "c:" << c;
    qDebug() << "d:" << d;

    double df = 127.793;
    double t_statistic = 9.77749;
    double ta = tprob(floor(df),-1.0 *t_statistic);
    double tb = tprob(floor(df), t_statistic);
    double t_prob = 1.0 - qAbs(ta - tb);

    qDebug() << "df:" << df;
    qDebug() << "t_statistic:" << t_statistic;
    qDebug() << "ta:" << ta;
    qDebug() << "tb:" << tb;
    qDebug() << "t_prob:" << t_prob;


    return 1;
}


double tprob(qint64 n, double x){
    if( n < 0 ){
    qDebug() << "[error] wrong n value input for tprob";
    exit(0);
    }

    double a,b,w,z,y,p;
    w=atan2(1.0 * x/sqrt(n),1);

    z=cos(w)*cos(w);
    y=1.0;
    p=0;

    for(qint64 i=n-2; i>=2;i-=2){
    y= 1 + 1.0 * (i-1)/i * z * y;
    }

    if( n%2 ==0){
    a=sin(w)/2;
    b=0.5;
    }else{
    a = (n==1)?0:sin(w)*cos(w)/PI;
    b = 0.5 + w/PI;
    }

    p = 1- b - a * y;

    if( p>0){
    return p;
    }else{
    return 0;
    }
}

输出:

a: 1.62448e-12
b: 1
c: 1
d: 1.62448e-12
df: 127.793
t_statistic: 9.77749
ta: 1
tb: 1.62457e-12
t_prob: 3.24907e-12

最佳答案

当您使用 << 打印浮点值时,默认情况下你只能得到 6 位精度或其他东西。

比较:

qDebug() << "c:" << c;
output: 1

与:

qDebug() << "c:" << QString("%1").arg(c, 0, 'g', 15);
output: "0.999999999998376"

所以 tprob = 1.0 - qAbs(ta - tb) = 1.0 - qAbs(1.0 - epsilon - epsilon) = 2*epsilon

关于c++ - 用C++计算小双数时出错,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35367375/

相关文章:

c++ - 文件不存在 - 相关错误。构建开源应用程序 QCAD 的问题

c++ - 如何创建空的工作 boost::python::dict?

java - 在施工时双重优先于 float

c++ - 枚举变量作为动态模板参数

c++ - 声明内联函数 noexcept 有意义吗?

c++ - 如果首先使用非常量初始化,为什么允许对 const 的非常量引用?

c++ - 什么是 [in] 和 [out]?

Qt 按钮槽被调用两次,尽管被禁用

mysql - MySQL 中丢失小数点

java - 为什么我在 Java/Android 中得到空 SQLite 字段的 "0.0"?