using System;
using System.Linq.Expressions;
using System.Diagnostics;
using System.Threading;
namespace ConsoleApplication
{
class Foo
{
public int Baz { get; set; }
}
class Program
{
static void Main(string[] args)
{
// Process.GetCurrentProcess().PriorityClass = ProcessPriorityClass.High;
const int cycles = 10000;
dynamic lambda;
Func<object, bool> lambda2;
Delegate lambda3;
Func<Foo, bool> lambda4;
Type theType = typeof(Foo);
Expression right = Expression.Constant(1);
{
ParameterExpression pe = Expression.Parameter(theType, "f");
Expression left = Expression.Property(pe, theType.GetProperty("Baz"));
Expression expr = Expression.Equal(left, right);
// This works fine but uses a hard-coded type, which I won't know until runtime:
lambda = Expression.Lambda(expr, new ParameterExpression[] { pe }).Compile();
lambda3 = Expression.Lambda(expr, new ParameterExpression[] { pe }).Compile(); ;
}
{
ParameterExpression pe = Expression.Parameter(typeof(object), "f");
Expression pe2 = Expression.Convert(pe, theType);
Expression left = Expression.Property(pe2, theType.GetProperty("Baz"));
Expression expr = Expression.Equal(left, right);
lambda2 = Expression.Lambda<Func<object, bool>>(expr, new ParameterExpression[] { pe }).Compile();
}
{
ParameterExpression pe = Expression.Parameter(typeof(Foo), "f");
Expression pe2 = Expression.Convert(pe, theType);
Expression left = Expression.Property(pe2, theType.GetProperty("Baz"));
Expression expr = Expression.Equal(left, right);
lambda4 = Expression.Lambda<Func<Foo, bool>>(expr, new ParameterExpression[] { pe }).Compile();
}
var t = new Foo { Baz = 1 };
for (int i = 0; i < 1000; i++)
{
lambda(t);
lambda2(t);
lambda3.DynamicInvoke(t);
lambda4(t);
}
Thread.Sleep(1000);
Stopwatch sw = Stopwatch.StartNew();
for (int i = 0; i < cycles; i++)
{
if (!lambda(t))
{
throw new Exception();
}
}
sw.Stop();
Stopwatch sw2 = Stopwatch.StartNew();
for (int i = 0; i < cycles; i++)
{
if (!lambda2(t))
{
throw new Exception();
}
}
sw2.Stop();
Stopwatch sw3 = Stopwatch.StartNew();
for (int i = 0; i < cycles; i++)
{
if (!(bool)lambda3.DynamicInvoke(t))
{
throw new Exception();
}
}
sw3.Stop();
Stopwatch sw4 = Stopwatch.StartNew();
for (int i = 0; i < cycles; i++)
{
if (!lambda4(t))
{
throw new Exception();
}
}
sw4.Stop();
Console.WriteLine("{0,12} dynamic", sw.ElapsedTicks);
Console.WriteLine("{0,12} Func<object, bool>", sw2.ElapsedTicks);
Console.WriteLine("{0,12} Delegate.DynamicInvoke", sw3.ElapsedTicks);
Console.WriteLine("{0,12} Func<Foo, bool>", sw4.ElapsedTicks);
}
}
}