Objective-C中部分iPhone设备出现Double转String转换异常问题
Hey, I’ve dealt with similar weird NSNumberFormatter edge cases before, and this almost certainly boils down to device locale settings—your current code uses the system’s default locale, which works fine locally, but a small number of users must have non-standard region configurations that are throwing off the formatter’s parsing of the decimal point.
What’s Causing This?
NSNumberFormatter defaults to following the user’s device locale. While most locales use a dot or comma for decimals, some rare custom configurations or niche region settings might have an empty or invalid decimal separator. When combined with your slightly imprecise double value (10.890000000000001, a common binary floating-point quirk), the formatter fails to recognize the decimal split and merges the integer and fractional parts into a single number: 1089.
Fixes You Can Implement
The most reliable fix is to force the formatter to use a fixed, machine-friendly locale (like en_US_POSIX), which doesn’t change based on user settings. Here’s your updated code:
NSNumberFormatter *formatter = [[NSNumberFormatter alloc] init]; // Lock in a consistent locale to avoid system-specific formatting formatter.locale = [NSLocale localeWithLocaleIdentifier:@"en_US_POSIX"]; [formatter setMaximumFractionDigits:2]; [formatter setRoundingMode:NSNumberFormatterRoundCeiling]; // Optional: Set minimum fraction digits if you want to ensure trailing zeros for whole numbers // [formatter setMinimumFractionDigits:0]; NSString *numberString = [formatter stringFromNumber:[NSNumber numberWithDouble:doubleValue]];
If you don’t need the full flexibility of NSNumberFormatter, you can also bypass it entirely while matching your rounding logic:
// Apply ceiling rounding first (matches your original NSNumberFormatterRoundCeiling) double roundedValue = ceil(doubleValue * 100) / 100; // Format directly with fixed decimal places NSString *numberString = [NSString stringWithFormat:@"%.2f", roundedValue];
Pro Tips for Future
- Never rely on the default locale for values that need consistent formatting (like prices, API payloads, or user-facing numbers that should look the same everywhere). Always explicitly set a locale.
- For precise numeric work (especially currency), use
NSDecimalNumberinstead ofdoubleto avoid binary floating-point precision errors entirely.
内容的提问来源于stack exchange,提问作者Jayaseelan Kumarasamy

