使用大数字时,函数pow()无法正常工作?

时间:2017-03-23 16:37:06

标签: c pow

请解释为什么pow()不适用于2 ^ 63这样的大数字?(如果你用pow(long long int a, long long int b)而不是pow(double a, double b)的原型编写一个pow函数,它可以正常工作。 )

这是代码:

#include <stdio.h>
#include <math.h>
int main()
{
    printf("%.0lf\n" ,pow((double)2,63));
}

输出:

9223372036854775800

真实答案:

9223372036854775808

感谢。

2 个答案:

答案 0 :(得分:4)

printf("%.0lf\n", x);不需要打印(double) x完全值。

兼容的C编译器/标准C库将生成将打印约DBL_DECIMAL_DIG(通常为17),正确重要十进制数字的代码。其他可能正确打印更多数字。 (我打印9223372036854775808)。见<float.h>

// 45678901234567
9223372036854775800 // answer
9223372036854775808 // true answer:

极端的例子

DBL_MAX可能有exact value

179769313486231570814527423731704356798070567525844996598917476803157260780028538760589558632766878171540458953514382464234321326889464182768467546703537516986049910576551282076245490090389328944075868508455133942304583236903222948165808559332123348274797826204144723168738177180919299881250404026184124858368

printf("%.0lf\n" ,DBL_MAX);的许多结果会在某个点之后报告零

179769313486231570814527423731704356798070600000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000

OP later added,引用pow()函数为long long int pow(long long int a, long long int b)。预计pow_ll_version(2,63)将导致9223372036854775808,其中1传递了许多LLONG_MAX - 当然是未定义的行为。我们假设它包装-9223372036854775808,并打印了printf("%llu\n" , long_long_int_result);(更多UB作为错误匹配的说明符和类型)。这可能给了9223372036854775808 OP。

printf()整数输出是精确的,浮点值不是这样。

答案 1 :(得分:0)

pow运行正常。 MSVC的printf是错误的,并且会截断浮点的输出。