我注意到 decimal.Parse(number, NumberStyles.AllowDecimalPoint, CultureInfo.InvariantCulture)
的速度比基于Jeffrey Sax代码的自定义十进制解析方法慢了大约100%。Jeffrey Sax代码来源于“Convert.ToDouble的更快替代方案”
public static decimal ParseDecimal(string input) {
bool negative = false;
long n = 0;
int len = input.Length;
int decimalPosition = len;
if (len != 0) {
int start = 0;
if (input[0] == '-') {
negative = true;
start = 1;
}
for (int k = start; k < len; k++) {
char c = input[k];
if (c == '.') {
decimalPosition = k +1;
} else {
n = (n *10) +(int)(c -'0');
}
}
}
return new decimal(((int)n), ((int)(n >> 32)), 0, negative, (byte)(len -decimalPosition));
}
我认为这是因为原生的 decimal.Parse
方法旨在处理数字样式和文化信息。
然而,上述方法没有使用 new decimal
中的第三个参数高字节,所以无法用于更大的数字。
是否有一种更快的替代方法来将仅由数字和小数点组成的字符串转换为可以处理大数字的十进制数?
编辑:基准测试:
var style = System.Globalization.NumberStyles.AllowDecimalPoint;
var culture = System.Globalization.CultureInfo.InvariantCulture;
System.Diagnostics.Stopwatch s = new System.Diagnostics.Stopwatch();
s.Reset();
s.Start();
for (int i=0; i<10000000; i++)
{
decimal.Parse("20000.0011223344556", style, culture);
}
s.Stop();
Console.WriteLine(s.Elapsed.ToString());
s.Reset();
s.Start();
for (int i=0; i<10000000; i++)
{
ParseDecimal("20000.0011223344556");
}
s.Stop();
Console.WriteLine(s.Elapsed.ToString());
输出:
00:00:04.2313728
00:00:01.4464048
在这种情况下,自定义的ParseDecimal比decimal.Parse快得多。