我有这段代码,当交换usingas和usingcast的顺序时,它们的性能也会交换。
using System;
using System.Diagnostics;
using System.Linq;
using System.IO;
class Test
{
const int Size = 30000000;
static void Main()
{
object[] values = new MemoryStream[Size];
UsingAs(values);
UsingCast(values);
Console.ReadLine();
}
static void UsingCast(object[] values)
{
Stopwatch sw = Stopwatch.StartNew();
int sum = 0;
foreach (object o in values)
{
if (o is MemoryStream)
{
var m = (MemoryStream)o;
sum += (int)m.Length;
}
}
sw.Stop();
Console.WriteLine("Cast: {0} : {1}", sum,
(long)sw.ElapsedMilliseconds);
}
static void UsingAs(object[] values)
{
Stopwatch sw = Stopwatch.StartNew();
int sum = 0;
foreach (object o in values)
{
if (o is MemoryStream)
{
var m = o as MemoryStream;
sum += (int)m.Length;
}
}
sw.Stop();
Console.WriteLine("As: {0} : {1}", sum,
(long)sw.ElapsedMilliseconds);
}
}
输出:
As: 0 : 322
Cast: 0 : 281
做这个的时候…
UsingCast(values);
UsingAs(values);
…结果如下:
Cast: 0 : 322
As: 0 : 281
当你这样做的时候…
UsingAs(values);
…结果如下:
As: 0 : 322
当你这样做的时候:
UsingCast(values);
…结果如下:
Cast: 0 : 322
除了独立运行它们之外,如何
使无效
缓存,所以被基准测试的第二个代码不会接收第一个代码的缓存内存?
撇开基准测试不谈,我很喜欢现代处理器实现这种缓存魔力的事实:-)
[编辑]
正如建议尝试这个更快的代码(假设)……
static void UsingAsAndNullTest(object[] values)
{
Stopwatch sw = Stopwatch.StartNew();
int sum = 0;
foreach (object o in values)
{
var m = o as MemoryStream;
if (m != null)
{
sum += (int)m.Length;
}
}
sw.Stop();
Console.WriteLine("As and null test: {0} : {1}", sum,
(long)sw.ElapsedMilliseconds);
}
……结果是:
As and null test: 0 : 342
比上面两个代码慢
[编辑]:
按照建议,每一个程序都要有自己的副本…
static void UsingAs(object[] values)
{
object[] a = values.ToArray();
Stopwatch sw = Stopwatch.StartNew();
int sum = 0;
foreach (object o in a)
{
if (o is MemoryStream)
{
var m = o as MemoryStream;
sum += (int)m.Length;
}
}
sw.Stop();
Console.WriteLine("As: {0} : {1}", sum,
(long)sw.ElapsedMilliseconds);
}
static void UsingCast(object[] values)
{
object[] a = values.ToArray();
Stopwatch sw = Stopwatch.StartNew();
int sum = 0;
foreach (object o in a)
{
if (o is MemoryStream)
{
var m = (MemoryStream)o;
sum += (int)m.Length;
}
}
sw.Stop();
Console.WriteLine("Cast: {0} : {1}", sum,
(long)sw.ElapsedMilliseconds);
}
…输出:
Cast: 0 : 282
As: 0 : 282
现在他们有同样的结果了,谢谢雷姆斯!
运行cast和独立运行时,它们也会产生相同的结果(即282)。现在,至于他们为什么
更快
(从322毫秒到282毫秒)当他们拿到自己的数组副本时,我无法从中得到任何东西:-)那完全是另一回事