CS50 贪婪需要建议

CS50 Greedy Need Advice

我正在做 cs50 问题集 "Greedy"。基本上是询问用户欠了多少零钱,然后输出与输入金额相等的最小硬币数量。它工作得很好,除了当我输入 4.2 它输出 22 而它应该输出 18.

#include <cs50.h>
#include <stdio.h>


int main(void)
{
    float n;
    do
    {
        n = get_float("How much change is owed?\n");
    }
    while(n == EOF);

    int cents = (int)(n * 100);
    int minimumamountofcoins = 0;
    if (cents/25 >= 1){
        while (cents/25 >= 1)
        {
            cents -= 25;
            minimumamountofcoins++;
        }

    }
    if (cents/10 >= 1){
        while (cents/10 >= 1)
        {
            cents -= 10;
            minimumamountofcoins++;
        }
    }
    if(cents/5 >= 1){
        while (cents/5 >= 1)
        {
            cents -= 5;
            minimumamountofcoins++;
        }
    }
    if (cents/1 >= 1){
        while (cents/1 >= 1)
        {
            cents -= 1;
            minimumamountofcoins++;
        }
    }
    printf("The minimum amount of coins is %d\n", minimumamountofcoins);
}

看起来这是从 float 到 int 的转换的问题。当您尝试将美元转换为美分时,您可以使用以下代码行:

int cents = (int)(n * 100);

然而,这行代码,对于 4.20 美元,返回 419 分值。这是舍入和浮点数的问题,因为 4.2 * 100 返回 419.99999999 而不是 420.0000000,整数转换截断而不是舍入. 4.18 美元也会出现此问题,可能还有其他值。

为防止出现这种情况,请在转换前添加 0.5,如下所示:

int cents = (int)(n * 100 + 0.5);

这将确保四舍五入发生在正确的方向,因为你永远不会因为一个微不足道的浮点数错误而偏离。

使用 math.h 库,您还可以使用 roundf() 函数,该函数将在负数的情况下起作用,以防万一。

int cents = (int)(roundf(n*100));

使用四舍五入函数对您的数字进行四舍五入。在您的这部分代码中,您需要添加圆函数。

int cents = (int)(n * 100);

必须是这样的:

cents = round(n * 100);

如果您还有其他此类问题,可以使用调试器,例如 debug50,在其中通过单击行号右侧的 来放置断点,然后在终端 window(其中你执行 clang) 你应该输入:

~/pset1/cash/ $ debug50 ./cash

或者你的程序叫什么。这将打开调试器,您将在其中找到所有变量以及它们等于什么。按播放按钮旁边的按钮向前移动一行代码。