使用string.EndsWith方法是别忘了用StringComparison.Ordinal!
程序员文章站
2022-03-08 23:09:40
...
今天项目(C#项目)中遇到了一个性能问题,在对一个10万字左右文本解析时速度特别慢,用Profiler调查了一下原来大多时间都用在了String.EndsWith这个方法上。 大家现在看下面一段程序。
var sb = new StringBuilder(100000); for (var i = 0; i < 10000; i++) { sb.Append("ABCDEFGHIJ"); } var text = sb.ToString(); var sw = new Stopwatch(); sw.Start(); for (var i = 0; i < 10000; i++) { var b = text.EndsWith("AAAA"); } sw.Stop(); Console.WriteLine(sw.ElapsedMilliseconds);
大家觉得这段程序大概要执行多长时间?
在我的机器上:36782 毫秒
大家再看这段代码
var sb = new StringBuilder(100000); for (var i = 0; i < 10000; i++) { sb.Append("ABCDEFGHIJ"); } var text = sb.ToString(); var sw = new Stopwatch(); sw.Start(); for (var i = 0; i < 10000; i++) { var b = text.EndsWith("AAAA", StringComparison.Ordinal); } sw.Stop(); Console.WriteLine(sw.ElapsedMilliseconds);
仅仅加了一个StringComparison.Ordinal, 执行时间是0,也就是不到1毫秒。
之前一直做java的项目,对于java里的String的endsWith出了比较字符串以外没有任何悬念。所以习惯性的在C#里也这样用。 但是在C#里,StringComparison.Ordinal才是常规用法。因为:
1. 用了它EndsWith会非常快
2. 一般情况下就是你想要的比较方式
使用StringComparison.Ordinal的比较方式就是我们常用的把字符当纯数字的比较方式。
如果不加这个参数, String的EndsWith的比较方式是culture-sensitive的,相当于EndsWith(str, StringComparison.CurrentCulture)。 这个是什么概念呢。 简单来讲就是某些语言上,虽然字符不同但是在语言上是相同的。
例如在德语环境下:
static void Main(string[] args) { Console.WriteLine("Grüße".EndsWith("sse", StringComparison.Ordinal)); Console.WriteLine("Grüße".EndsWith("sse", StringComparison.CurrentCulture)); Console.WriteLine("Grüße".EndsWith("sse", StringComparison.InvariantCulture)); Console.WriteLine("Grüße".EndsWith("sse")); }
得到的结果是:
False
True
True
True
上一篇: 并发编程之 CAS 的原理