CFNumberFormatterCreateStringWithNumber int issue

193 Views Asked by At

I'm seeing an issue with CFNumberFormatterCreateStringWithNumber. I used this Apple code example:

// Works fine with float:
float n = 1.20;
CFNumberRef value = CFNumberCreate(NULL, kCFNumberFloatType, &n);
CFLocaleRef currentLocale = CFLocaleCopyCurrent();
// Create different number formatters
CFNumberFormatterRef decimalFormatter = CFNumberFormatterCreate(NULL, currentLocale, kCFNumberFormatterDecimalStyle);
CFStringRef decimalString = CFNumberFormatterCreateStringWithNumber(NULL, decimalFormatter, value);

// Using an INT I see an issue
int n = 892385;
CFNumberRef value = CFNumberCreate(NULL, kCFNumberSInt32Type, &n);
CFLocaleRef currentLocale = CFLocaleCopyCurrent();
// Create different number formatters
CFNumberFormatterRef decimalFormatter = CFNumberFormatterCreate(NULL, currentLocale, kCFNumberFormatterDecimalStyle);
CFStringRef decimalString = CFNumberFormatterCreateStringWithNumber(NULL, decimalFormatter, value);
/// release, release, release

The error I see when using an INT value (instead of float) is:

<CFNumber 0x5ac27 [0x7fff9856ed80]>{value = +1452, type = kCFNumberSInt32Type}
2017-03-05 21:42:06.789577 HID_Dumper[4390:150864] -[__NSCFNumber _getCString:length:multiplier:]: unrecognized selector sent to instance 0x2e4027
2

There are 2 best solutions below

0
On

Your code up there empirically worked for me. I only needed to make a couple of cosmetic changes:

#import <CoreFoundation/CoreFoundation.h>

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        // insert code here...
        NSLog(@"Hello, World!");

        // Works fine with float:
        float n = 1.20;
        CFNumberRef value = CFNumberCreate(NULL, kCFNumberFloatType, &n);
        CFLocaleRef currentLocale = CFLocaleCopyCurrent();
        // Create different number formatters
        CFNumberFormatterRef decimalFormatter = CFNumberFormatterCreate(NULL, currentLocale, kCFNumberFormatterDecimalStyle);
        CFStringRef decimalString = CFNumberFormatterCreateStringWithNumber(NULL, decimalFormatter, value);
        NSLog(@"float is %@", (__bridge NSString *)decimalString);
        CFRelease(decimalFormatter);
        CFRelease(decimalString);

        // Using an INT I see an issue
        SInt32 duh = 892385;
        value = CFNumberCreate(NULL, kCFNumberSInt32Type, &duh);
        currentLocale = CFLocaleCopyCurrent();
        // this is the exact same formatter as up there...
        decimalFormatter = CFNumberFormatterCreate(NULL, currentLocale, kCFNumberFormatterDecimalStyle);
        decimalString = CFNumberFormatterCreateStringWithNumber(NULL, decimalFormatter, value);

        NSLog(@"integer is %@", (__bridge NSString *)decimalString);
        /// release, release, release
        CFRelease(decimalFormatter);
        CFRelease(decimalString);
    }
    return 0;
}

which results in an output of:

2017-03-05 22:31:49.502 Testing[3278:221264] Hello, World!
2017-03-05 22:31:49.510 Testing[3278:221264] float is 1.2
2017-03-05 22:31:49.511 Testing[3278:221264] integer is 892,385
Program ended with exit code: 0
0
On

It turns out this didn't work because I was compiling and running from C++ code (.cpp extensions) and it DOES WORK when I switch the file's extension to .mm (Objective-C++)