冷回清风暖 发表于 2020-2-28 15:48:51

s1e6最后一个动手题 为什么用sum += pow(2,i)输出的结果是0


程序
#include<stdio.h>
#include<math.h>

int main()
{
    unsigned long long sum = 0,weight,temp;
    for(int i = 0 ; i < 64 ; i ++)
    {
      //temp = pow(2,i);
      sum += pow(2,i);
    }

    weight = sum/25000;
    printf("舍罕王要兑现他的许诺共要%llu粒麦子赏赐他的宰相\n",sum);
    printf("如果每25000粒麦子重1kg,那么舍罕王应该给予达依尔%llu公斤麦子\n",weight);

    return 0;
}
结果

舍罕王要兑现他的许诺共要0粒麦子赏赐他的宰相
如果每25000粒麦子重1kg,那么舍罕王应该给予达依尔0公斤麦子

Process returned 0 (0x0)   execution time : 1.046 s
Press any key to continue.

qiuyouzhi 发表于 2020-2-28 15:54:13

如果不用+=的话,sum只会单纯的加一下,并不会赋值进sum

冷回清风暖 发表于 2020-2-28 16:09:52

qiuyouzhi 发表于 2020-2-28 15:54
如果不用+=的话,sum只会单纯的加一下,并不会赋值进sum

第十行sum += pow(2,i);用了+= 不应该是等同于 sum = sum + pow(2,i);吗
但是为什么结果是0呢

SHRS23 发表于 2020-2-28 16:12:01

数据类型错误 pow 函数 的 参数和返回值都是 double 类型!
#include<stdio.h>
#include<math.h>

int main()
{
    double sum = 0,weight,temp;
    int i = 0 ;
    for(i = 0 ; i < 64 ; i ++)
    {
      //temp = pow(2,i);
      sum += pow(2.0,(double)i);
    }

    weight = sum/25000;
    printf("舍罕王要兑现他的许诺共要%f粒麦子赏赐他的宰相\n",sum);
    printf("如果每25000粒麦子重1kg,那么舍罕王应该给予达依尔%f公斤麦子\n",weight);

    return 0;
}

需要说明的是对于循环语句i处的修改是因为我的编译器不支持在循环中定义i,所以我修改到循环外定义,对本问题无影响。

另外我不确定double是否满足这道题的数据长度要求,C99标准有 long double 这个数据类型,输入出时需要使用%Lf(区别于 double 输入 %lf 输出 %f )
如果long double 仍然不够,你可以了解一下 高精度算法 ,但是这样就需要你重新编写pow函数

qiuyouzhi 发表于 2020-2-28 16:15:36

冷回清风暖 发表于 2020-2-28 16:09
第十行用了+= 不应该是等同于 吗
但是为什么结果是0呢

得先用temp存储一哈pow的值
#include<stdio.h>
#include<math.h>

int main()
{
    unsigned long long int sum = 0,weight,temp;
    for(int i = 0 ; i < 64 ; i++)
    {
      temp = pow(2,i);
      sum += temp;
    }

    weight = sum/25000;
    printf("舍罕王要兑现他的许诺共要%llu粒麦子赏赐他的宰相\n",sum);
    printf("如果每25000粒麦子重1kg,那么舍罕王应该给予达依尔%llu公斤麦子\n",weight);

    return 0;
}

qiuyouzhi 发表于 2020-2-28 16:17:43

冷回清风暖 发表于 2020-2-28 16:09
第十行用了+= 不应该是等同于 吗
但是为什么结果是0呢

得先将pow的值存到变量里
#include<stdio.h>
#include<math.h>

int main()
{
    unsigned long long int sum = 0,weight,temp;
    for(int i = 0 ; i < 64 ; i++)
    {
      temp = pow(2,i);
      sum += temp;
    }

    weight = sum/25000;
    printf("舍罕王要兑现他的许诺共要%llu粒麦子赏赐他的宰相\n",sum);
    printf("如果每25000粒麦子重1kg,那么舍罕王应该给予达依尔%llu公斤麦子\n",weight);

    return 0;
}

chxchxkkk 发表于 2020-2-28 16:26:27

用devc++会出现你图上的情况,而用vs2019则能正常输出。可能是devc++不支持这么大的整数,数据溢出了,所以输出0.

major_lyu 发表于 2020-2-28 17:34:07

因为pow函数的定义是:double power(double x, double y)。因此返回值是一个double 类型的数据。
因此 sum += pow(2,i)的结果数现将sum转换成double类型,然后与pow(2,i)的值相加,然后将得到的double类型的数据赋给sum。
改成sum+=(unsigned long long)pow(2,i)在进行加法运算前将数据类型强制转换成unsigned long long类型就可以避免出现错误。
另外,数据这么大了就直接用float或者double类型存储sum呗,unsigned long long 最大就只能存储0xFFFF FFFF FFFF FFFF。你这已经到达sum能够存储的极限数据了
页: [1]
查看完整版本: s1e6最后一个动手题 为什么用sum += pow(2,i)输出的结果是0