计算给定更改量的方式的数量

时间:2011-10-19 06:16:19

标签: c++ algorithm floating-point currency

我试图编写一个算法来计算使用给定面额制作一定数量的不同可能方式的数量。 假设美元的面额分别为100美元,50美元,20美元,10美元,5美元,1美元,0.25美元,0.10美元,0.05美元和0.01美元。下面的函数,适用于int amount和int denominations

/* Count number of ways of making different combination */
int Count_Num_Ways(double amt, int numDenom, double S[]){
   cout << amt << endl; //getchar();

  /* combination leads to the amount */
  if(amt == 0.00)
    return 1;

  /* No combination can lead to negative sum*/
  if(amt < 0.00)
    return 0;

  /* All denominations have been exhausted and we have not reached
     the required sum */
  if(numDenom < 0 && amt >= 0.00)
    return 0;

  /* either we pick this denomination, this causes a reduction of 
     picked denomination from the sum for further subproblem, or 
     we choose to not pick this denomination and 
     try a different denomination */
   return Count_Num_Ways(amt, numDenom - 1, S) + 
          Count_Num_Ways(amt - S[numDenom], numDenom, S);
}

但是当我将逻辑从int更改为float时,它会进入无限循环。我怀疑这是因为代码中的浮点比较。我无法弄清楚无限循环行为的确切原因。 在这方面的任何帮助都会有所帮助。

2 个答案:

答案 0 :(得分:8)

当处理这种“小”货币金额并且不处理利息时,仅处理美分和整数金将更容易,而不是使用浮点数。

所以只需将公式更改为使用美分而不是美元并继续使用整数。然后,当你需要显示金额时,只需将它们除以100即可获得美元和模数100来获得美分。

答案 1 :(得分:4)

由于有限的表示,

浮点运算不能精确。这样你永远不会得到0.0。这就是为什么你总是测试这样的间隔:

if (fabs(amt - 0.0) < TOL)

给定的容差为TOLTOL被恰当地选择用于申请,在这种情况下,1/2美分应该已经很好了。

编辑:当然,对于这种事情,Daemin的答案更合适。