【问题标题】:Calculating the total amount of change given计算给定的总变化量
【发布时间】:2016-04-22 04:56:54
【问题描述】:

您好,我目前正在关注 Computing with C# 和 .NET Framework 这本书,但我在其中一项练习中遇到了困难,即

编写一个 C# 程序进行更改。输入低于 1 美元的项目的成本。输出 以硬币形式提供的硬币,使用 25 美分、硬币、镍和便士。使用最少的硬币 可能的。例如,如果该物品的价格为 17 美分,则变化将是四分之三,一美分, 还有三便士

由于我仍在尝试掌握 c# 编程,因此我想出的最佳方法是使用 while 循环。

while(costOfItem >= 0.50)
            {
                costOfItem -= 0.50;
                fiftyPence++;
            }

我有这些用于 20、10、5 等便士的每一个。 我正在检查金额是否大于或等于 50 便士,如果是,我从用户给出的金额中减少 50 便士,并将 1 加到 50 便士变量中。

然后它进入下一个 while 循环,我对每个便士都有这个循环。问题是,在某个循环带走的某处,假设是 20 便士,costOfItem 变成类似于“0.1999999999999”的东西,然后它永远不会下降到 0,它应该得到正确的变化量。

感谢任何帮助,请不要建议我尚未涵盖的复杂程序。

【问题讨论】:

  • 你用什么类型的单位来支付给的钱?
  • costOfItem 使用什么数据类型?听起来像是float,如果是这样,你应该试试decimal
  • 你需要用decimal来代表钱。 doublefloat 之类的浮点类型不合适,会导致此类问题。见this related question

标签: c# loops while-loop


【解决方案1】:

切勿将doublefloat 用于金钱操作。使用Decimal。 对于计算准确性的所有其他问题,您必须使用“双 Epsilon 比较”,例如 Double.Epsilon for equality, greater than, less than, less than or equal to, greater than or equal to

【讨论】:

    【解决方案2】:

    如果你用美分计算,你可以使用整数,这样你就不会遇到浮点舍入问题

    【讨论】:

    • 这称为磨坊表示,基于磨坊货币。所有操作都基于整数。 1000 Mill = 1 美元。
    【解决方案3】:

    听起来你正在使用floatdouble 作为costOfItem 的数据类型。
    floatdouble 以二进制形式存储它们的值。但并非所有十进制值都有二进制的精确表示。因此,存储了一个非常接近的近似。这就是为什么你会得到像“0.1999999999999”这样的值。

    对于金钱计算,您应该始终使用decimal,因为它们可以避免那些小错误。

    您可以阅读更多关于Jon Skeets awesome answerDifference between Decimal, Float and Double in .NET? 的区别

    【讨论】:

      【解决方案4】:

      感谢大家的快速回复。问题是我使用 double 而不是 decimal 提供的链接让人们解释为什么在某些情况下这样做是错误的。在算术中应避免使用 double,因为显然某些浮点数没有精确的二进制表示,因此它给出的不是 0.23,而是 0.2299999999999。将变量更改为十进制解决了我的问题

      【讨论】:

        猜你喜欢
        • 2018-09-20
        • 1970-01-01
        • 1970-01-01
        • 2021-10-30
        • 2019-03-13
        • 2017-03-05
        • 1970-01-01
        • 2015-12-15
        • 1970-01-01
        相关资源
        最近更新 更多