这是一个简单的问题,我在论坛上搜索,但找不到答案(我发现了一个关于Log但我不认为这里有舍入错误。)
我编写了一个程序来确定一系列过期产品的罚款价值,但是当比率准确时,程序将返回下一个罚款类别,忽略条件中的=符号。
该计划必须退还以下罚款:
这是我写的代码:
#include <stdio.h>
int calculate_fine(int ncheckedproducts, int nexpiredproducts)
{
int fine;
float ratio;
ratio=(float)nexpiredproducts/ncheckedproducts;
if(nexpiredproducts==0)
fine=0;
else
if(ratio<=0.1)
fine=100;
else
if(ratio<=0.3)
fine=10000;
else
fine=100000;
return fine;
}
int main(void)
{
int ncheckedproducts, nexpiredproducts, fine;
printf("Type number of checked and expired products\n");
scanf("%d %d", &ncheckedproducts, &nexpiredproducts);
fine=calculate_fine(ncheckedproducts, nexpiredproducts);
printf("The fine is: %d\n", fine);
return 0;
}
但是对于100和10,以及100和30的值,分别是过期产品的10%和30%,程序将返回错误的罚款。
老师没有向我解释原因,并纠正了以下功能:
int calculate_fine(int ncheckedproducts, int nexpiredproducts)
{
int fine;
if(nexpiredproducts==0)
fine=0;
else
if(nexpiredproducts<=0.1*ncheckedproducts)
fine=100;
else
if(nexpiredproducts<=0.3*ncheckedproducts)
fine=10000;
else
fine=100000;
return fine;
}
但是,我想知道为什么前10%的比率大于0.1,为什么我不能使用这种方法。
答案 0 :(得分:1)
这很可能是一个舍入问题,但与你想象的不同:许多有限小数部分没有有限的二进制分数表示。因此,一些舍入最接近的数字可以表示为给定类型的浮点数。
答案 1 :(得分:1)
您正在处理的是浮点数的细粒度方面:
计算机以二进制格式保存浮点数。你的浮动可能是IEEE-754 single precision floating point number。
在这些格式中,您通常只能表示仅仅是非常有限的两个幂的总和的数字;例如,0.75是2 -1 + 2 -2 ,因此可以精确地重建。在你的情况下,你尝试将100 = 2 6 + 2 5 + 2 2 除以3 = 2 1 +2 0 并希望得到与0.3 = 2 -2 + 2 -5 + 2 -9完全相同的结果 + 2 -10 + 2 -13 + ...
那不会发生。