Skip to content

Commit 4020e05

Browse files
authored
Clean up in Number.Formatting.cs (#110955)
1 parent 94add2e commit 4020e05

File tree

1 file changed

+10
-113
lines changed

1 file changed

+10
-113
lines changed

src/libraries/System.Private.CoreLib/src/System/Number.Formatting.cs

Lines changed: 10 additions & 113 deletions
Original file line numberDiff line numberDiff line change
@@ -268,11 +268,11 @@ internal static partial class Number
268268
300;
269269
#endif
270270
/// <summary>Lazily-populated cache of strings for uint values in the range [0, <see cref="SmallNumberCacheLength"/>).</summary>
271-
private static readonly string[] s_smallNumberCache = new string[SmallNumberCacheLength];
271+
private static readonly string?[] s_smallNumberCache = new string[SmallNumberCacheLength];
272272

273273
// Optimizations using "TwoDigits" inspired by:
274274
// https://engineering.fb.com/2013/03/15/developer-tools/three-optimization-tips-for-c/
275-
private static readonly byte[] TwoDigitsCharsAsBytes =
275+
private static ReadOnlySpan<byte> TwoDigitsCharsAsBytes =>
276276
MemoryMarshal.AsBytes<char>("00010203040506070809" +
277277
"10111213141516171819" +
278278
"20212223242526272829" +
@@ -282,9 +282,9 @@ internal static partial class Number
282282
"60616263646566676869" +
283283
"70717273747576777879" +
284284
"80818283848586878889" +
285-
"90919293949596979899").ToArray();
286-
private static readonly byte[] TwoDigitsBytes =
287-
("00010203040506070809"u8 +
285+
"90919293949596979899");
286+
private static ReadOnlySpan<byte> TwoDigitsBytes =>
287+
"00010203040506070809"u8 +
288288
"10111213141516171819"u8 +
289289
"20212223242526272829"u8 +
290290
"30313233343536373839"u8 +
@@ -293,7 +293,7 @@ internal static partial class Number
293293
"60616263646566676869"u8 +
294294
"70717273747576777879"u8 +
295295
"80818283848586878889"u8 +
296-
"90919293949596979899"u8).ToArray();
296+
"90919293949596979899"u8;
297297

298298
public static unsafe string FormatDecimal(decimal value, ReadOnlySpan<char> format, NumberFormatInfo info)
299299
{
@@ -387,9 +387,8 @@ private static int GetFloatingPointMaxDigitsAndPrecision(char fmt, ref int preci
387387

388388
int maxDigits = precision;
389389

390-
switch (fmt)
390+
switch (fmt | 0x20)
391391
{
392-
case 'C':
393392
case 'c':
394393
{
395394
// The currency format uses the precision specifier to indicate the number of
@@ -404,7 +403,6 @@ private static int GetFloatingPointMaxDigitsAndPrecision(char fmt, ref int preci
404403
break;
405404
}
406405

407-
case 'E':
408406
case 'e':
409407
{
410408
// The exponential format uses the precision specifier to indicate the number of
@@ -423,9 +421,7 @@ private static int GetFloatingPointMaxDigitsAndPrecision(char fmt, ref int preci
423421
break;
424422
}
425423

426-
case 'F':
427424
case 'f':
428-
case 'N':
429425
case 'n':
430426
{
431427
// The fixed-point and number formats use the precision specifier to indicate the number
@@ -440,7 +436,6 @@ private static int GetFloatingPointMaxDigitsAndPrecision(char fmt, ref int preci
440436
break;
441437
}
442438

443-
case 'G':
444439
case 'g':
445440
{
446441
// The general format uses the precision specifier to indicate the number of significant
@@ -457,7 +452,6 @@ private static int GetFloatingPointMaxDigitsAndPrecision(char fmt, ref int preci
457452
break;
458453
}
459454

460-
case 'P':
461455
case 'p':
462456
{
463457
// The percent format uses the precision specifier to indicate the number of
@@ -476,7 +470,6 @@ private static int GetFloatingPointMaxDigitsAndPrecision(char fmt, ref int preci
476470
break;
477471
}
478472

479-
case 'R':
480473
case 'r':
481474
{
482475
// The roundtrip format ignores the precision specifier and always returns the shortest
@@ -1579,7 +1572,7 @@ internal static unsafe void WriteTwoDigits<TChar>(uint value, TChar* ptr) where
15791572

15801573
Unsafe.CopyBlockUnaligned(
15811574
ref *(byte*)ptr,
1582-
ref Unsafe.Add(ref MemoryMarshal.GetArrayDataReference(typeof(TChar) == typeof(char) ? TwoDigitsCharsAsBytes : TwoDigitsBytes), (uint)sizeof(TChar) * 2 * value),
1575+
ref Unsafe.Add(ref MemoryMarshal.GetReference(typeof(TChar) == typeof(char) ? TwoDigitsCharsAsBytes : TwoDigitsBytes), (uint)sizeof(TChar) * 2 * value),
15831576
(uint)sizeof(TChar) * 2);
15841577
}
15851578

@@ -1595,7 +1588,7 @@ internal static unsafe void WriteFourDigits<TChar>(uint value, TChar* ptr) where
15951588

15961589
(value, uint remainder) = Math.DivRem(value, 100);
15971590

1598-
ref byte charsArray = ref MemoryMarshal.GetArrayDataReference(typeof(TChar) == typeof(char) ? TwoDigitsCharsAsBytes : TwoDigitsBytes);
1591+
ref byte charsArray = ref MemoryMarshal.GetReference(typeof(TChar) == typeof(char) ? TwoDigitsCharsAsBytes : TwoDigitsBytes);
15991592

16001593
Unsafe.CopyBlockUnaligned(
16011594
ref *(byte*)ptr,
@@ -1677,7 +1670,7 @@ internal static unsafe void WriteDigits<TChar>(uint value, TChar* ptr, int count
16771670
return bufferEnd;
16781671
}
16791672

1680-
internal static unsafe string UInt32ToDecStr(uint value)
1673+
internal static string UInt32ToDecStr(uint value)
16811674
{
16821675
// For small numbers, consult a lazily-populated cache.
16831676
if (value < SmallNumberCacheLength)
@@ -2540,102 +2533,6 @@ private static unsafe bool TryUInt128ToDecStr<TChar>(UInt128 value, int digits,
25402533
return false;
25412534
}
25422535

2543-
private static ulong ExtractFractionAndBiasedExponent(double value, out int exponent)
2544-
{
2545-
ulong bits = BitConverter.DoubleToUInt64Bits(value);
2546-
ulong fraction = (bits & 0xFFFFFFFFFFFFF);
2547-
exponent = ((int)(bits >> 52) & 0x7FF);
2548-
2549-
if (exponent != 0)
2550-
{
2551-
// For normalized value, according to https://en.wikipedia.org/wiki/Double-precision_floating-point_format
2552-
// value = 1.fraction * 2^(exp - 1023)
2553-
// = (1 + mantissa / 2^52) * 2^(exp - 1023)
2554-
// = (2^52 + mantissa) * 2^(exp - 1023 - 52)
2555-
//
2556-
// So f = (2^52 + mantissa), e = exp - 1075;
2557-
2558-
fraction |= (1UL << 52);
2559-
exponent -= 1075;
2560-
}
2561-
else
2562-
{
2563-
// For denormalized value, according to https://en.wikipedia.org/wiki/Double-precision_floating-point_format
2564-
// value = 0.fraction * 2^(1 - 1023)
2565-
// = (mantissa / 2^52) * 2^(-1022)
2566-
// = mantissa * 2^(-1022 - 52)
2567-
// = mantissa * 2^(-1074)
2568-
// So f = mantissa, e = -1074
2569-
exponent = -1074;
2570-
}
2571-
2572-
return fraction;
2573-
}
2574-
2575-
private static ushort ExtractFractionAndBiasedExponent(Half value, out int exponent)
2576-
{
2577-
ushort bits = BitConverter.HalfToUInt16Bits(value);
2578-
ushort fraction = (ushort)(bits & 0x3FF);
2579-
exponent = ((int)(bits >> 10) & 0x1F);
2580-
2581-
if (exponent != 0)
2582-
{
2583-
// For normalized value, according to https://en.wikipedia.org/wiki/Half-precision_floating-point_format
2584-
// value = 1.fraction * 2^(exp - 15)
2585-
// = (1 + mantissa / 2^10) * 2^(exp - 15)
2586-
// = (2^10 + mantissa) * 2^(exp - 15 - 10)
2587-
//
2588-
// So f = (2^10 + mantissa), e = exp - 25;
2589-
2590-
fraction |= (ushort)(1U << 10);
2591-
exponent -= 25;
2592-
}
2593-
else
2594-
{
2595-
// For denormalized value, according to https://en.wikipedia.org/wiki/Half-precision_floating-point_format
2596-
// value = 0.fraction * 2^(1 - 15)
2597-
// = (mantissa / 2^10) * 2^(-14)
2598-
// = mantissa * 2^(-14 - 10)
2599-
// = mantissa * 2^(-24)
2600-
// So f = mantissa, e = -24
2601-
exponent = -24;
2602-
}
2603-
2604-
return fraction;
2605-
}
2606-
2607-
private static uint ExtractFractionAndBiasedExponent(float value, out int exponent)
2608-
{
2609-
uint bits = BitConverter.SingleToUInt32Bits(value);
2610-
uint fraction = (bits & 0x7FFFFF);
2611-
exponent = ((int)(bits >> 23) & 0xFF);
2612-
2613-
if (exponent != 0)
2614-
{
2615-
// For normalized value, according to https://en.wikipedia.org/wiki/Single-precision_floating-point_format
2616-
// value = 1.fraction * 2^(exp - 127)
2617-
// = (1 + mantissa / 2^23) * 2^(exp - 127)
2618-
// = (2^23 + mantissa) * 2^(exp - 127 - 23)
2619-
//
2620-
// So f = (2^23 + mantissa), e = exp - 150;
2621-
2622-
fraction |= (1U << 23);
2623-
exponent -= 150;
2624-
}
2625-
else
2626-
{
2627-
// For denormalized value, according to https://en.wikipedia.org/wiki/Single-precision_floating-point_format
2628-
// value = 0.fraction * 2^(1 - 127)
2629-
// = (mantissa / 2^23) * 2^(-126)
2630-
// = mantissa * 2^(-126 - 23)
2631-
// = mantissa * 2^(-149)
2632-
// So f = mantissa, e = -149
2633-
exponent = -149;
2634-
}
2635-
2636-
return fraction;
2637-
}
2638-
26392536
private static ulong ExtractFractionAndBiasedExponent<TNumber>(TNumber value, out int exponent)
26402537
where TNumber : unmanaged, IBinaryFloatParseAndFormatInfo<TNumber>
26412538
{

0 commit comments

Comments
 (0)