title: Improve performance of obtaining MethodInfo from MethodCallExpression
body: <p>Our UI system can generate a form from a MethodInfo.  Before System.Linq.Expressions, we were getting the MethodInfo using reflection (method 1):</p>
  
  <pre><code>MethodInfo info = typeof(ExtensionTestClass).GetMethod("InstanceMethod", BindingFlags.Public | BindingFlags.Instance, null, new Type[] { typeof(string), typeof(string) }, null);
  </code></pre>
  
  <p>The bad part about this is that if we changed the signature or name of InstanceMethod, the code would still compile.  </p>
  
  <p>Enter expressions.  Now we do this (method 2):</p>
  
  <pre><code> MethodInfo info = GetMethod&lt;ExtensionTestClass&gt;(x =&gt; x.InstanceMethod("defaultValue", "defaultValue"));
  </code></pre>
  
  <p>or this (method 3):</p>
  
  <pre><code>MethodInfo info = GetMethod&lt;ExtensionTestClass, string, string&gt;(x =&gt; x.InstanceMethod);
  </code></pre>
  
  <p>The syntax is "better", we get intellisense, and we get compilation errors if the method doesn't exist or the signature doesn't match.  However, method 2 and method 3 are about 10 to 20 times slower than reflection. </p>
  
  <p>Some numbers (measured with StopWatch):</p>
  
  <p>Single Call:
  Method 1:  .0000565
  Method 2:  .0004272
  Method 3:  .0019222</p>
  
  <p>100000 Calls:
  Method 1:  .1171071
  Method 2: 1.5648544
  Method 3: 2.0602607</p>
  
  <p>We don't actually compile the expression or execute it, and I'm interested if anyone has an explanation for the difference in performance.</p>
  
  <p>UPDATE:  The GetMethod&lt;> code:</p>
  
  <p>Method 2:</p>
  
  <pre><code>public static MethodInfo GetMethod&lt;T&gt;(Expression&lt;Action&lt;T&gt;&gt; target)
  {
      MethodCallExpression exp = target.Body as MethodCallExpression;
      if (exp != null)
      {
          return exp.Method;
      }
      return null;
  }
  </code></pre>
  
  <p>Method 3:</p>
  
  <pre><code>public static MethodInfo GetMethod&lt;T, A1, A2&gt;(Expression&lt;Func&lt;T, Action&lt;A1, A2&gt;&gt;&gt; expression)
  {
      var lambdaExpression = (LambdaExpression)expression;
      var unaryExpression = (UnaryExpression)lambdaExpression.Body;
      var methodCallExpression = (MethodCallExpression)unaryExpression.Operand;
      var methodInfoExpression = (ConstantExpression)methodCallExpression.Arguments.Last();
      return (MethodInfo)methodInfoExpression.Value;
  }
  </code></pre>