iOS小技能:金额格式处理 (货币符号本地化)

携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第12天,点击查看活动详情

引言

iOS 系统自带格式化NSFormatter的常用子类有:NSNumberFormatter(数字格式化)、NSDateFormatter(NSISO8601DateFormatter日期格式化)、NSPersonNameComponentsFormatter(名片格式化)、NSMeasurementFormatter(数量单位格式化)。

在这里插入图片描述

本文侧重内容;金额格式处理的应用场景(根据需求格式化日期、数字,如商品的金额。)

在这里插入图片描述

原理:利用NSNumberFormatter进行处理

@interface NSNumberFormatter : NSFormatter {







I 金额的格式转化处理(NSNumberFormatter)

number format styles

 94863
 NSNumberFormatterNoStyle = kCFNumberFormatterNoStyle,

 94,862.57
 NSNumberFormatterDecimalStyle = kCFNumberFormatterDecimalStyle,



 ¥94,862.57
 NSNumberFormatterCurrencyStyle = kCFNumberFormatterCurrencyStyle,



 9,486,257%
 NSNumberFormatterPercentStyle = kCFNumberFormatterPercentStyle,


 9.486257E4
 NSNumberFormatterScientificStyle = kCFNumberFormatterScientificStyle,


 九万四千八百六十二点五七
 NSNumberFormatterSpellOutStyle = kCFNumberFormatterSpellOutStyle

1.1 获取货币符号

FOUNDATION_EXPORT NSLocaleKey const NSLocaleCurrencySymbol;      // NSString
//        获取货币符号的正确方式formatter.locale = [NSLocale currentLocale];
            NSString* currencySymbol = [NSLocale.currentLocale objectForKey:NSLocaleCurrencySymbol];//这里获取到的就是货币符号,例如:¥、$等等






去掉货币符号和负号

//







+ (NSString*)getAmountStr:(NSString*)topNO{
    NSLog( @"func: %s", __func__ );




    if([topNO containsString:@","] || [topNO containsString:@"," ]){
        
        return topNO;
        
    }
    
    


    NSString *tmp = [QCT_Common stringChangeMoneyWithStr:topNO numberStyle:NSNumberFormatterCurrencyStyle];



    


    if ([topNO doubleValue]<0) {// 去掉负号
        
//删除指定字符串的方法
        tmp=  [tmp stringByReplacingOccurrencesOfString:@"-" withString:@""];//
                
        

    }
    //去掉货币符号
                NSString* currencySymbol = [NSLocale.currentLocale objectForKey:NSLocaleCurrencySymbol];//这里获取到的就是货币符号,例如:¥、$等等


    tmp = [tmp stringByReplacingOccurrencesOfString:currencySymbol withString:@""];
    

    
    return tmp;
}




1.2 金额字段(简单处理)











    return  FMSTR(@"%0.2f",self.refundableAmount);// 金融字段处理
    //@property (nonatomic,assign)  double refundableAmount;//




. 避免出现这样的错误<total_fee><![CDATA[7.000000000000001]]></total_fee>

  • 元转分
/**

 元转分
 
 %d:整数
 %f:浮点数
 %s:方法
 %c:c字符
 %@:OC对象
 %p:指针
 //保留两位小数
 NSLog(@"%0.2f",1.0203);
 输出结果:1.02



 //使用0左补位
 NSLog(@"%04d",1);
 输出结果:0001




 //使用空格左补位
 NSLog(@"%4d",1);
 输出结果:   1


 //字符串补位
 NSLog(@"%4s!","a");
 输出结果:   a!


 //字符串右补位
 NSLog(@"%-4s!","a");
 输出结果:a   !


 <total_fee><![CDATA[7]]></total_fee>
 total_fee Int  类型
 */
+ (NSString*)changeY2FWithStr:(NSString*)paymentAmount{
    
    NSNumber *tm  = [NSNumber numberWithDouble:paymentAmount.doubleValue*100];
    return  FMSTR(@"%ld",(long)tm.integerValue);// 
    //    return  FMSTR(@"%0.2f",tm.doubleValue);//浮点数会报参数错误
    
}

1.3 金额字段(CurrencyStyle)

在这里插入图片描述

  • 用法
    //没有间隙的人民币符号:零售价:¥2.00
    //中文输入法的人民币符号:   ¥
    self.priceLab.text =[NSString stringWithFormat:@"%@%@",QCTLocal(@"retail_price_"),[QCT_Common  getAmountStr4CurrencyStyle:models.sysPrice]];










  • 金额的格式转化
风格 对应的枚举 输出样式
四舍五入的整数 NSNumberFormatterNoStyle 12346
小数形式 NSNumberFormatterDecimalStyle 12,345.678
货币形式(已本地化处理) NSNumberFormatterCurrencyStyle $12,345.68
百分数形式 NSNumberFormatterPercentStyle 1,234,568%
科学计数 NSNumberFormatterScientificStyle 1.2345678E4
朗读形式 NSNumberFormatterSpellOutStyle twelve thousand three hundred forty-five point six seven eight
序数形式 NSNumberFormatterOrdinalStyle 12,346th
货币形式(已本地化处理) NSNumberFormatterCurrencyISOCodeStyle USD12,345.68
货币形式(已本地化处理) NSNumberFormatterCurrencyPluralStyle 12,345.68 US dollars
会计计数 NSNumberFormatterCurrencyAccountingStyle $12,345.68



/**

 NSNumberFormatterCurrencyStyle 货币形式(已本地化处理)
 
 带货币符号
 //        获取货币符号的正确方式formatter.locale = [NSLocale currentLocale];
 //            NSString* currencySymbol = [NSLocale.currentLocale objectForKey:NSLocaleCurrencySymbol];//这里获取到的就是货币符号,例如:¥、$等等
         



 */
+ (NSString*)getAmountStr4CurrencyStyle:(NSString*)topNO{
    


    if([topNO containsString:@","] || [topNO containsString:@"," ]){
        
        return topNO;
        
    }
    


    
    NSString *tmp = [QCT_Common stringChangeMoneyWithStr:topNO numberStyle:NSNumberFormatterCurrencyStyle];
        

    if ([topNO doubleValue]<0) {// 去掉负号
        NSMutableString *tmpstr = [[NSMutableString alloc]initWithString:tmp];
        
//删除指定字符串的方法
        tmp = [tmpstr stringByReplacingOccurrencesOfString:@"-" withString:@""];//
    //   NSRange r1 = [tmp rangeOfString:currencySymbol];//查找字符串(返回一个结构体(起始位置及长度))
    // - (void)deleteCharactersInRange:(NSRange)range;//删除一个范围内的字符串


                
    }
    
    

    return tmp;
}





/**
 * 金额的格式转化
 * str : 金额的字符串
 * numberStyle : 金额转换的格式
 * return  NSString : 转化后的金额格式字符串
 
 /**
 * 94863
 * NSNumberFormatterNoStyle = kCFNumberFormatterNoStyle,
 
 * 94,862.57
 * NSNumberFormatterDecimalStyle = kCFNumberFormatterDecimalStyle,
 
 * ¥94,862.57
 * NSNumberFormatterCurrencyStyle = kCFNumberFormatterCurrencyStyle,
 
 * 9,486,257%
 * NSNumberFormatterPercentStyle = kCFNumberFormatterPercentStyle,
 
 * 9.486257E4
 * NSNumberFormatterScientificStyle = kCFNumberFormatterScientificStyle,
 
 * 九万四千八百六十二点五七
 * NSNumberFormatterSpellOutStyle = kCFNumberFormatterSpellOutStyle
 
 */
+ (NSString *)stringChangeMoneyWithStr:(NSString *)str numberStyle:(NSNumberFormatterStyle)numberStyle {
    
    // 判断是否null 若是赋值为0 防止崩溃
    if (([str isEqual:[NSNull null]] || str == nil)) {
        str = 0;
    }
    
    NSNumberFormatter *formatter = [[NSNumberFormatter alloc]init];
    formatter.locale = [NSLocale currentLocale];
    formatter.numberStyle = numberStyle;
    // 注意传入参数的数据长度,可用double
    NSString *money = [formatter stringFromNumber:[NSNumber numberWithDouble:[str doubleValue]]];
    
    

    
    return money;
}



1.4 自定义格式:#,###.00元

在这里插入图片描述

原理:利用 NSNumberFormatter 的 numberStyle 和 positiveFormat 属性

//自定义格式:`#,###.00元`
- (NSString *)formatDecimalNumber:(NSString *)string {
 if (!string || string.length == 0) {
 return string;
 }
  
 NSNumber *number = @([string doubleValue]);
 NSNumberFormatter *formatter = [[NSNumberFormatter alloc] init];
 formatter.numberStyle = kCFNumberFormatterDecimalStyle;
 //如果不用.00的样式,整数格式化后不会保留小数,因为kCFNumberFormatterDecimalStyle就是这样处理整数格式的。
 formatter.positiveFormat = @"#,##0.00元";
  
 NSString *amountString = [formatter stringFromNumber:number];
 return amountString;
}

1.5 其他样式

    // 小数点样式
    numberFormatter.decimalSeparator = @".";
    

    // 零的样式
    numberFormatter.zeroSymbol       = @"-";
    

    // 正前缀和后缀
    numberFormatter.positivePrefix = @"!";
    numberFormatter.positiveSuffix = @"元";
    // 负前缀和后缀
    numberFormatter.negativePrefix = @"@";
    numberFormatter.negativeSuffix = @"钱";
    // 整数最多位数
    numberFormatter.maximumIntegerDigits = 110;
    


    // 整数最少位数
    numberFormatter.minimumIntegerDigits = 2;
    


    // 小数位最多位数
    numberFormatter.maximumFractionDigits = 3;
    
    // 小数位最少位数
    numberFormatter.minimumFractionDigits = 1;
    
    // 数字分割的尺寸
    numberFormatter.groupingSize = 4;
    

    // 除了groupingSize决定的尺寸外,其他数字位分割的尺寸
    numberFormatter.secondaryGroupingSize = 2;
    
    // 最大有效数字个数
    numberFormatter.maximumSignificantDigits = 12;
    

    // 最少有效数字个数
    numberFormatter.minimumSignificantDigits = 3;
    // 四色五入方式
    numberFormatter.roundingMode = kCFNumberFormatterRoundHalfUp;

II 时间格式化(NSDateFormatter)

blog.csdn.net/z929118967/…

@interface NSISO8601DateFormatter : NSFormatter <NSSecureCoding> {







@interface NSDateFormatter : NSFormatter {






GGG: 公元时代,例如AD公元
yy: 年的后2位
yyyy: 完整年
MM: 月,显示为1-12
MMM: 月,显示为英文月份简写,如 Jan
MMMM: 月,显示为英文月份全称,如 Janualy
dd: 日,2位数表示,如02
d: 日,1-2位显示,如 2
EEE: 简写星期几,如Sun
EEEE: 全写星期几,如Sunday
aa: 上下午,AM/PM
H: 时,24小时制,0-23
K:时,12小时制,0-11
m: 分,1-2位
mm: 分,2位
s: 秒,1-2位
ss: 秒,2位
S:毫秒
zzz:三位字符串表示“时区”(例如GMT)。缩写 Z

2.1 系统自带的样式

date and time format styles

typedef NS_ENUM(NSUInteger, NSDateFormatterStyle) {    //     NSDateFormatterNoStyle = kCFDateFormatterNoStyle,
    NSDateFormatterShortStyle = kCFDateFormatterShortStyle,
    NSDateFormatterMediumStyle = kCFDateFormatterMediumStyle,
    NSDateFormatterLongStyle = kCFDateFormatterLongStyle,
    NSDateFormatterFullStyle = kCFDateFormatterFullStyle
};

格式 日期 时间
NSDateFormatterNoStyle “” “”
NSDateFormatterShortStyle 2022/7/31 上午11:40
NSDateFormatterMediumStyle 2022年7月31日 上午11:40:29
NSDateFormatterLongStyle 2022年7月31日 GMT+8 上午11:40:49
NSDateFormatterFullStyle 2022年7月31日 星期三 中国标准时间 上午11:41:16

2.2 自定义日期格式化

  1. 案例1: 小程序订单小票

在这里插入图片描述

  1. 案例2:订单详情时间格式化

在这里插入图片描述

setDateFormat

  1. stringFromDate:
  2. dateFromString:
+ (NSString *)date4ateFormat:(NSString *)DateFormat withdate:(NSDate *)date{
    


    NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
    [formatter setDateStyle:NSDateFormatterMediumStyle];
    [formatter setTimeStyle:NSDateFormatterShortStyle];
    [formatter setDateFormat:DateFormat];
    
    return [formatter stringFromDate:date];
}
//[QCT_Common dateWithFormatterString:tmpbirthday dateFormat:@"yyyy-MM-dd HH:mm:ss"]
+ (NSDate*)dateWithFormatterString:(NSString*)dateWithString dateFormat:(NSString*)dateFormat {
    


    NSDateFormatter *dateFormatter = [[NSDateFormatter alloc]init];
    dateFormatter.locale = [[NSLocale alloc] initWithLocaleIdentifier:@"zh_CN"];
    dateFormatter.dateFormat = dateFormat;
    NSDate *date = [dateFormatter dateFromString:dateWithString];
    return date;
    


}



III 数量单位格式化

3.1 单位时间




/**

@property (class, readonly, copy) NSUnitDuration *hours;
@property (class, readonly, copy) NSUnitDuration *minutes;
@property (class, readonly, copy) NSUnitDuration *seconds;



*/
- (void)testNSUnitDuration{
    
    NSMeasurementFormatter *formatter = [[NSMeasurementFormatter alloc] init];
        [formatter setLocale:[[NSLocale alloc] initWithLocaleIdentifier:@"zh"]];


    [formatter setUnitOptions:NSMeasurementFormatterUnitOptionsProvidedUnit];



    


    
    NSMeasurement *measurement = [[NSMeasurement alloc] initWithDoubleValue:600 unit:NSUnitDuration.seconds];// 600秒



    NSMeasurement *measurement11 = [measurement measurementByConvertingToUnit:NSUnitDuration.minutes];//10分钟



    NSLog(@"seconds: %@",[formatter stringFromMeasurement:measurement]); //seconds: 600 sec


    

    NSLog(@"minutes: %@",[formatter stringFromMeasurement:measurement11]); //10 min
    
    NSMeasurement *measurement1 = [[NSMeasurement alloc] initWithDoubleValue:12 unit:NSUnitAcceleration.metersPerSecondSquared];
    NSLog(@"metersPerSecondSquared: %@",[formatter stringFromMeasurement:measurement1]); //12米/秒²

    
    NSMeasurement *measurement2 = [[NSMeasurement alloc] initWithDoubleValue:12 unit:NSUnitAcceleration.gravity];//
    NSLog(@"gravity: %@",[formatter stringFromMeasurement:measurement2]); //12G





}




列表 对应类 基础单位
加速度单位 NSUnitAcceleration m /s²
几何角度单位 NSUnitAngle 度(°)
面积单位 NSUnitArea 平方米(m²)
单元集中质量(密度) NSUnitConcentrationMass 毫克/分升(mg / dL)
单位分散 NSUnitDispersion 百万分率(ppm)
单位时间 NSUnitDuration 秒(s)
单位电荷 NSUnitElectricCharge 库仑(C)
单位电流 NSUnitElectricCurrent 安(A)
单位电位差(电压) NSUnitElectricCurrent 伏特(V)
单元电阻 NSUnitElectricResistance 欧姆(Ω)
单位能量 NSUnitEnergy 焦耳(J)
单位频率 NSUnitFrequency 赫兹(赫兹)
单位燃料效率 NSUnitFuelEfficiency 每百公里升(L / 100km)
单位长度 NSUnitLength 米(m)
单位照度 NSUnitIlluminance 勒克斯(lx)
单位质量 NSUnitMass 千克(kg)
单位功率 NSUnitPower 瓦特(W)
单位压力 (压强) NSUnitPressure 牛顿每平方米(N /m²)
单位速度 NSUnitSpeed 米/秒(m / s)
单位温度 NSUnitTemperature 开尔文(K)
单位体积 NSUnitVolume 升(L)

3.2 字节转换

@interface NSByteCountFormatter : NSFormatter 







- (void)testNSByteCountFormatter{
    

    
    NSByteCountFormatter *format = [[NSByteCountFormatter alloc] init];
     //以MB输出
    format.allowedUnits = NSByteCountFormatterUseMB;
    //1024字节为1KB
    format.countStyle = NSByteCountFormatterCountStyleBinary;
    // 输出结果显示单位
    format.includesUnit =  YES;
    // 输出结果显示数据
    format.includesCount = YES;
    //是否显示完整的字节
    format.includesActualByteCount = YES;







    NSString *str = [format stringFromByteCount:1024*1024];
    

    NSLog(@"NSByteCountFormatter: %@",str);// 1 MB (1,048,576 bytes)


    



}

3.3 长度单位

- (void)testNSLengthFormatter{
    


    

    //长度单位
    NSLengthFormatter  *lengthFormatter = [[NSLengthFormatter alloc] init];
    

    [lengthFormatter.numberFormatter setLocale:[[NSLocale alloc] initWithLocaleIdentifier:@"zh"]];
    

    lengthFormatter.unitStyle = NSFormattingUnitStyleLong;
    /// 输出 200米
    NSString *lengthOutputString1 = [lengthFormatter stringFromValue:200 unit:NSLengthFormatterUnitMeter];
    NSLog(@" 输出 NSLengthFormatterUnitMeter: %@",lengthOutputString1);



    /// 输出 30米
    NSString *lengthOutputString2 = [lengthFormatter stringFromMeters:30];



    NSLog(@" 输出 stringFromMeters: %@",lengthOutputString2);



    /// 输出 meters
    NSString *lengthOutputString3 = [lengthFormatter unitStringFromValue:33333.2 unit:NSLengthFormatterUnitMeter];
    NSLog(@" 输出 NSLengthFormatterUnitMeter: %@",lengthOutputString3);
}



3.4 能量格式化

- (void)NSEnergyFormatter







{
    

    //能量格式化(卡cal)
    NSEnergyFormatter *formatter = [[NSEnergyFormatter alloc] init];
    formatter.forFoodEnergyUse = YES;
    

    [formatter.numberFormatter setLocale:[[NSLocale alloc] initWithLocaleIdentifier:@"zh_CN"]];


    NSString *outputString = [formatter stringFromJoules:1000.0];
    NSLog(@" 输出 stringFromJoules: %@",outputString);//1,000焦耳



    


}




3.5 质量格式化

- (void)testNSMassFormatter{
    


    //质量格式化
    NSMassFormatter *massFormatter = [[NSMassFormatter alloc] init];
    [massFormatter.numberFormatter setLocale:[[NSLocale alloc] initWithLocaleIdentifier:@"zh_CN"]];
    massFormatter.unitStyle = NSFormattingUnitStyleLong;
    /// 输出 200克
    NSString *outputString1 = [massFormatter stringFromValue:200 unit:NSMassFormatterUnitGram];
    NSLog(@" 输出 NSMassFormatterUnitGram: %@",outputString1);


    /// 输出 200千克
    NSString *outputString2 = [massFormatter stringFromKilograms:200];
    NSLog(@" 输出 stringFromKilograms: %@",outputString2);



    /// 输出 kilograms
    NSString *outputString3 = [massFormatter unitStringFromValue:1111 unit:NSMassFormatterUnitKilogram];
    
    NSLog(@" 输出 NSMassFormatterUnitKilogram: %@",outputString3);


    



}



V 名片格式化

名片对象和名片格式化字符串的快速转换,最核心的还是在于locale属性对名片信息进行本地化(根据不同的语言环境进行格式化)。

/* Specifies the locale to format names. Defaults to autoupdatingCurrentLocale. Also resets to autoupdatingCurrentLocale on assignment of nil.
 */
@property (null_resettable, copy) NSLocale *locale API_AVAILABLE(macos(12.0), ios(15.0), watchos(8.0), tvos(15.0));






[formatter setLocale:[[NSLocale alloc] initWithLocaleIdentifier:@"zh"]];



  1. personNameComponentsFromString:
/**

 NSPersonNameComponents
>An object that manages the separate parts of a person's name to allow locale-aware formatting.






*/
//通过固定格式的字符串快速创建名片信息:@"Dr. Gregory John Casamento PhD"
void runTests()
{



    NSPersonNameComponents *pnc = [[NSPersonNameComponents alloc] init];
    [pnc setGivenName: @"Gregory"];
    [pnc setMiddleName: @"John"];
    [pnc setFamilyName: @"Casamento"];
    [pnc setNameSuffix: @"PhD"];
    [pnc setNamePrefix: @"Dr."];



NSPersonNameComponents *pnc2 = [fmt personNameComponentsFromString:
                                    @"Dr. Gregory John Casamento PhD"];


    passTest([[pnc givenName] isEqualToString:
              [pnc2 givenName]], @"First name matches");
    passTest([[pnc middleName] isEqualToString:
              [pnc2 middleName]], @"Middle name matches");
    passTest([[pnc familyName] isEqualToString:
              [pnc2 familyName]], @"Family name matches");
    passTest([[pnc nameSuffix] isEqualToString:
              [pnc2 nameSuffix]], @"Suffix name matches");
    passTest([[pnc namePrefix] isEqualToString:
              [pnc2 namePrefix]], @"Prefix name matches");




}
/* Show whether test was passed */
void passTest(BOOL flag,
              NSString *msg)
{
    if(flag == YES)
    {
        NSLog(@"PASS: %@",msg);
    }
    else
    {
        NSLog(@"FAIL: %@",msg);
    }
}


  1. stringFromPersonNameComponents:
//NSPersonNameComponentsFormatter







//@interface NSPersonNameComponentsFormatter : NSFormatter 










    NSPersonNameComponentsFormatter *formatter = [[NSPersonNameComponentsFormatter alloc] init];
    NSPersonNameComponents *p = [[NSPersonNameComponents alloc] init];
    p.givenName = @"名字";
    p.familyName = @"姓";
    p.nameSuffix = @"后缀";
    p.namePrefix = @"前缀";
    p.nickname = @"昵称";
    p.middleName = @"中间符号";
    NSString *outputString1 =[formatter stringFromPersonNameComponents:p];
    formatter.style = NSPersonNameComponentsFormatterStyleLong;







typedef NS_ENUM(NSInteger, NSPersonNameComponentsFormatterStyle) {
    NSPersonNameComponentsFormatterStyleDefault = 0,



    /* Relies on user preferences and language defaults to display shortened form appropriate
      for display in space-constrained settings, e.g. C Darwin */
    NSPersonNameComponentsFormatterStyleShort,


    /* The minimally necessary features for differentiation in a casual setting , e.g. Charles Darwin */
    NSPersonNameComponentsFormatterStyleMedium,

    /* The fully-qualified name complete with all known components, e.g. Charles Robert Darwin, FRS */
    NSPersonNameComponentsFormatterStyleLong,


    /* The maximally-abbreviated form of a name suitable for monograms, e.g. CRD) */
    NSPersonNameComponentsFormatterStyleAbbreviated
} API_AVAILABLE(macos(10.11), ios(9.0), watchos(2.0), tvos(9.0));


*/



see also

iOS处理语言工具CFStringTransform : 智能地处理用户的输入内容,经典应用场景【索引】

通讯录demo源码:https://download.csdn.net/download/u011018979/19088189
1、原理:通过对用户输入内容,利用CFStringTransform变换,可以轻松实现实现一个通用的搜索index
2、 特色:搜索内容可以是多语言的
3、文章:https://kunnan.blog.csdn.net/article/details/109603377

© 版权声明
THE END
喜欢就支持一下吧
点赞0

Warning: mysqli_query(): (HY000/3): Error writing file '/tmp/MYPaw48a' (Errcode: 28 - No space left on device) in /www/wwwroot/583.cn/wp-includes/class-wpdb.php on line 2345
admin的头像-五八三
评论 抢沙发
头像
欢迎您留下宝贵的见解!
提交
头像

昵称

图形验证码
取消
昵称代码图片