NSDecimalNumber是NSNumber的子类,比NSNumber的功能更为强大,可以指定一个数的幂,四舍五入等操作。NSString类型转化成CGFloat、CGDouble类型,使用floatValue、doubleValue 等方法结果精度不高的情况。例如 @"8" -> 7.99999 @"1.0" -> 1.00001 @"12.9"->12.8999
由于NSDecimalNumber精度较高,所以会比基本数据类型费时,所以需要权衡考虑,苹果官方建议在货币以及要求精度很高的场景下使用。
一、一些科学计数法的简单方法。
//一个关于科学计数法的方法:参数 1.mantissa 实数 2.exponent 指数 3.flag 正负
- (instancetype)initWithMantissa:(unsigned long long)mantissa exponent:(short)exponent isNegative:(BOOL)flag;
+ (NSDecimalNumber *)decimalNumberWithMantissa:(unsigned long long)mantissa exponent:(short)exponent isNegative:(BOOL)flag;
例:mantissa = 6 ,exponent = 2 ,flag = false 结果:6*10^2 = 600。
//一个科学计数法的初始化方法:numberValue 字符串(详情见官方文档)
- (instancetype)initWithString:(nullable NSString *)numberValue;
+ (NSDecimalNumber *)decimalNumberWithString:(nullable NSString *)numberValue;
例:NSDecimalNumber *a = [[NSDecimalNumber alloc] initWithString:@"-4e3"]; 输出:-4000。
二、NSDecimalNumber 对象值进行操作
//一些基本赋值
+ (NSDecimalNumber *)zero; //Returns an NSDecimalNumber object equivalent to the number 1.0.
+ (NSDecimalNumber *)one; //Returns an NSDecimalNumber object equivalent to the number 0.0.
+ (NSDecimalNumber *)minimumDecimalNumber; //-340282366920938463463374607431768211455
+ (NSDecimalNumber *)maximumDecimalNumber;+ (NSDecimalNumber *)notANumber; //Returns an NSDecimalNumber object that specifies no number.非数字
例:enum { NSRoundPlain,//四舍五入
NSRoundDown,//只舍不入
NSRoundUp,//只入不舍NSRoundBankers
//近似于圆};
typedef NSUInteger NSRoundingMode;
//NSDecimalNumberBehaviors对象的创建 参数 1.RoundingMode 一个取舍枚举值 2.scale 处理范围 3.raiseOnExactness 精确出现异常是否抛出原因 4.raiseOnOverflow 上溢出是否抛出原因 4.raiseOnUnderflow 下溢出是否抛出原因 5.raiseOnDivideByZero 除以0是否抛出原因。
NSDecimalNumber * a = [NSDecimalNumber decimalNumberWithString:@"2.5301"];
NSDecimalNumber * b = [NSDecimalNumber decimalNumberWithString:@"7.5001"];
NSDecimalNumberHandler *roundingBehavior = [NSDecimalNumberHandler decimalNumberHandlerWithRoundingMode:NSRoundBankers scale:2 raiseOnExactness:NO raiseOnOverflow:NO raiseOnUnderflow:NO raiseOnDivideByZero:NO]
//加法运算 参数 behavior 对的到的结构做一些限制(后面有说明)
- (NSDecimalNumber *)decimalNumberByAdding:(NSDecimalNumber *)decimalNumber;
- (NSDecimalNumber *)decimalNumberByAdding:(NSDecimalNumber *)decimalNumber withBehavior:(nullable id)behavior;
NSDecimalNumber *c = [a decimalNumberByAdding:b]; 结果:10.032 NSDecimalNumber *c = [a decimalNumberByAdding:b withBehavior:roundingBehavior]; 结果:10.03
//减法运算
- (NSDecimalNumber *)decimalNumberBySubtracting:(NSDecimalNumber *)decimalNumber;
- (NSDecimalNumber *)decimalNumberBySubtracting:(NSDecimalNumber *)decimalNumber withBehavior:(nullable id)behavior;
NSDecimalNumber *c = [a decimalNumberBySubtracting:b]; 结果:-4.97 NSDecimalNumber *c = [a decimalNumberBySubtracting:b withBehavior:roundingBehavior]; 结果:-4.97
//乘法运算
- (NSDecimalNumber *)decimalNumberByMultiplyingBy:(NSDecimalNumber *)decimalNumber;
- (NSDecimalNumber *)decimalNumberByMultiplyingBy:(NSDecimalNumber *)decimalNumber withBehavior:(nullable id)behavior;
NSDecimalNumber *c = [a decimalNumberByMultiplyingBy:b]; 结果:18.97600301
NSDecimalNumber *c = [a decimalNumberByMultiplyingBy:b withBehavior:roundingBehavior]; 结果:18.98
//除法运算
- (NSDecimalNumber *)decimalNumberByDividingBy:(NSDecimalNumber *)decimalNumber;
- (NSDecimalNumber *)decimalNumberByDividingBy:(NSDecimalNumber *)decimalNumber withBehavior:(nullable id)behavior;
NSDecimalNumber *c = [a decimalNumberByDividingBy:b]; 结果:0.3373421687710830522259703203957280
NSDecimalNumber *c = [a decimalNumberByDividingBy:b withBehavior:roundingBehavior]; 结果:0.34
//a的n次方 参数
- (NSDecimalNumber *)decimalNumberByRaisingToPower:(NSUInteger)power;- (NSDecimalNumber *)decimalNumberByRaisingToPower:(NSUInteger)power withBehavior:(nullable id)behavior;
NSDecimalNumber *c = [a decimalNumberByRaisingToPower:3]; 结果:16.196197345901
NSDecimalNumber *c = [a decimalNumberByRaisingToPower:3 withBehavior:roundingBehavior]; 结果:16.2
//指数运算
- (NSDecimalNumber *)decimalNumberByMultiplyingByPowerOf10:(short)power;
- (NSDecimalNumber *)decimalNumberByMultiplyingByPowerOf10:(short)power withBehavior:(nullable id)behavior;
//四舍五入
- (NSDecimalNumber *)decimalNumberByRoundingAccordingToBehavior:(nullable id)behavior;
NSDecimalNumber *c = [a decimalNumberByRoundingAccordingToBehavior:roundingBehavior]; 结果:2.53
//两数比较
- (NSComparisonResult)compare:(NSNumber *)decimalNumber;
NSLog(@"%ld",(long)[a compare:b]); 结果 -1.
//设置默认的behaviors对象
+ (void)setDefaultBehavior:(id)behavior;+ (id)defaultBehavior;
注:后面全部设为 NO 的话,默认只进行后两位的的四舍五入操作,再多就是直接舍去。 需要更精确的四舍五入需要scale后面参数某个改为YES。