它开始很正常。我正在为iPhone编写复杂的计算应用程序。我决定使用float原语来表示数字。所以,时间开始四舍五入和格式化输出,但首先是四舍五入。我想将数字舍入到不同的小数位数。 FOund out没有有用的C函数。好的,所以我可以写自己的。但随后我将应用程序设置中的数字保留下来。 我发现只有对象可以持久化。 所以我开始挖掘NSNumber和NSDecimalNumber。特别是后者只有在看时它才会让我颤抖。委托需要实现舍入,没有smiple算术运算符,而不是特殊方法.... :( 什么是纯粹的C简单?
还有其他方法可以简化这个吗?
答案 0 :(得分:3)
您可以使用theValue - fmod(theValue, 0.01)
舍入到此示例中,最接近0.01。)但要注意!
计算机实际上并不使用十进制数 - 即。基数十的数字,我们在正常生活中使用它们的方式。它们使用二进制数,包括浮点数。它们也以二进制表示,这意味着“小数位数”并不总是浮点数的有意义属性。
例如,浮点数不能精确地表示0.1,如果您尝试在代码中使用它,您将获得类似0.1000000001的值。您获得的确切值因实现而异,并且无法通过减去差异来纠正,因为计算机无法判断 是否存在差异 - 这与它可以达到0.1一样接近。< / p>
这就是NSDecimalNumber
这样的类存在的原因。他们模拟十进制数学,给出看起来更健全的价值观。它们容易出现许多与浮点相同的问题,但是具有不同的值(例如,1.0 / 3.0在十进制中不能完全表示,但它仍然是一个离散值。)
所以是的,如果你的数字必须四舍五入到特定的小数位数,你需要使用NSDecimalNumber
进行大多数小数运算。如果仅用于显示,则可以使用类似NSNumberFormatter
的内容来获取显示值,而无需在内存中修改数字本身。
问题的第二部分 - 在用户默认值中存储数值,很容易解决。 NSNumber
“包装”一个原始数字类型,但它可以解包:
NSNumber *n = [NSNumber numberWithDouble: 1.234567890];
double aDouble = [n doubleValue];
答案 1 :(得分:2)
每当您需要准确的准确度时,请使用NSDecimal
和NSDecimalNumber
,尤其是对于任何会计/财务内容。对于其他需要准确性的内容,但您不需要完全精度,请使用double
,而不是float
。 NSNumber
只是一个用于数字基元的Obj-C对象包装器。
要进行格式化和舍入,请查看NSNumberFormatter
。任何C原始数字都可以包含在NSNumber
中,然后您可以使用NSNumberFormatter
将其转换为NSString
。起初看起来有点笨拙,但在实际使用中,它的效果非常好,因为你可以获得非常高级别的格式控制。