iOS客户端手续费计算方法并解决金额精度问题

需求:
1.客户端模仿微信的提现功能,具体提现操作可以试玩一下你的微信提现操作;
2.提现涉及到手续费的计算,客户端计算的手续费和后台计算的手续费要进行对比,有点坑哈!
3.既然进行对比,那就要设定规则标准:

需要精确数值计算;
小数点后精确保留2位数字;
怎么舍去小数点2位后数字,小数点后两位之后若有数字都需进1(既然是提现,咋可不能吃亏呀!),也就是只入不舍或者是无穷舍进。

还有一些困难:用户在UITextField输入具体金额,我们拿到的数据也是NSString类型的金额,然后转化成CGFloat类型的等等进行计算,但是这样计算出来的数据值就不准确了,所以第1条必须要保证精确数值计算。
没办法,就找了下资料,找到了苹果有专门的API,针对金融货币单位:
NSDecimalNumber --> 解决计算NSString类型精度问题
NSDecimalNumberHandler --> 解决上面的就算结果如何取舍以及需要保留的精度(小数点位数)
希望可以解决有遇到同样问题的人。

- (void)viewDidLoad {
    [super viewDidLoad];
    // Do any additional setup after loading the view, typically from a nib.
    tempStr1 = @"88";
    tempStr2 = @"0.2%";
    [self decimalNumberMutiplyWithString:tempStr1 with:tempStr2];
}

/**
 客户端手续费计算方法并解决金额精度问题
 参考博客:
 http://www.th7.cn/Program/IOS/201608/937405.shtml
 http://blog.csdn.net/yuwuchaio/article/details/50637942

 @param amountValue 用户输入的具体金额
 @param rateValue 后台给予的费率
 @return 客户端计算出的手续费
 */
-(NSString *)decimalNumberMutiplyWithString:(NSString *)amountValue with:(NSString *)rateValue{
    /*手续费计算精度问题解决:NSDecimalNumber
     加减乘除:
     decimalNumberByAdding
     decimalNumberBySubtracting:
     decimalNumberByMultiplyingBy:
     decimalNumberByDividingBy:
     */
    NSDecimalNumber *rateValueNumber = [NSDecimalNumber decimalNumberWithString:rateValue];
    NSDecimalNumber *oneHundredValueNumber = [NSDecimalNumber decimalNumberWithString:[NSString stringWithFormat:@"%d", 100]];
    NSDecimalNumber *division = [rateValueNumber decimalNumberByDividingBy:oneHundredValueNumber];
    NSDecimalNumber *amountValueNumber = [NSDecimalNumber decimalNumberWithString:amountValue];
    NSDecimalNumber *product = [amountValueNumber decimalNumberByMultiplyingBy:division];
    NSLog(@"%@", [product stringValue]);
    /*四舍五入精确度问题解决:NSDecimalNumberHandler
     讲述下参数的含义:
     RoundingMode: 简单讲就是你要四舍五入操作的标准.
     枚举
     NSRoundPlain,   //Round up on a tie //貌似取整 
     NSRoundDown,    //Always down == truncate  //只舍不入
     NSRoundUp,      // Always up    //只入不舍
     NSRoundBankers  // on a tie round so last digit is even  貌似四舍五入
     scale : 需要保留的精度。
     raiseOnExactness : 为YES时在处理精确时如果有错误,就会抛出异常。
     raiseOnOverflow  : YES时在计算精度向上溢出时会抛出异常,否则返回。
     raiseOnUnderflow : YES时在计算精度向下溢出时会抛出异常,否则返回.
     raiseOnDivideByZero : YES时。当除以0时会抛出异常,否则返回。
     */
    NSDecimalNumberHandler *roundingBehavior = [NSDecimalNumberHandler decimalNumberHandlerWithRoundingMode:NSRoundUp scale:2 raiseOnExactness:NO raiseOnOverflow:NO raiseOnUnderflow:NO raiseOnDivideByZero:NO];
    NSString *tempStr =[[product decimalNumberByRoundingAccordingToBehavior:roundingBehavior] stringValue];
    NSLog(@"%@",tempStr);
    return tempStr;
}

暂时说到这里,后续也会持续更新优化,若有问题欢迎留言,共同探讨!!!

你可能感兴趣的:(iOS客户端手续费计算方法并解决金额精度问题)