技术开发 频道

C#和.NET不可忍受之慢 谁是罪魁祸首?

  【IT168 技术】前些日子,爆出N篇说C#/.NET太慢的,要求删除C#/.NET部分特性的文章。

  撇开那些文章不说,C#/.NET慢似乎是业界公认的铁则,不论大家如何证明C# / .NET其实不比C++慢多少,但是应用程序级别的性能却依然这么慢。

  那么C#/.NET慢在哪里?

  很不幸的是大部分c#程序是被大部分程序员拖慢的,也许这个结论不太容易被人接受,却是一个广泛存在的。

  String的操作

  几乎所有的程序都有String操作,至少90%的程序需要忽略大小写的比较,检查一下代码,至少其中大半的应用程序有类似这样的代码:

if (str1.ToUpper() == str2.ToUpper())

  或者ToLower版的,甚至我还看到过有个Web的HttpModule里面写上了:

for (int i = 0; i < strs.Count; i++)
if (value.ToUpper() == strs[i].ToUpper())
//...

  想一下,每个页面请求过来,都要执行这样一段代码,大片大片的创建string实例,更夸张的是还有人说这是用空间换时间。

  性能测试

  说这个方法慢,也许还有人不承认,认为这个就是最好的方法,所以这里要用具体测试来摆个事实。

  首先准备一个测试性能的方法:

PRivate static TResult MeasurePerformance<TArg, TResult>(Func<TArg, TResult> func, TArg arg, int loop)
{
GC.Collect();
int gc0 = GC.CollectionCount(0);
int gc1 = GC.CollectionCount(1);
int gc2 = GC.CollectionCount(2);
TResult result
= default(TResult);
Stopwatch sw
= Stopwatch.StartNew();
for (int i = 0; i < loop; i++)
{
result
= func(arg);
}
Console.WriteLine(sw.ElapsedMilliseconds.ToString()
+ "ms");
Console.WriteLine(
"GC 0:" + (GC.CollectionCount(0) - gc0).ToString());
Console.WriteLine(
"GC 1:" + (GC.CollectionCount(1) - gc1).ToString());
Console.WriteLine(
"GC 2:" + (GC.CollectionCount(2) - gc2).ToString());
return result;
}

  然后来准备一个堆string:

private static List<string> CreateStrings()
{
List
<string> strs = new List<string>(10000);
char[] chs = new char[3];
for (int i = 0; i < 10000; i++)
{
int j = i;
for (int k = 0; k < chs.Length; k++)
{
chs[k]
= (char)('a' + j % 26);
j
= j / 26;
}
strs.Add(
new string(chs));
}
return strs;
}
1
相关文章