title: Create Func or Action for any method (using reflection in c#)
body: <p>My application works with loading dll's dynamically, based on settings
  from the database (file, class and method names). To facilitate, expedite and reduce the use of reflection I would like to have a cache....</p>
  
  <p>Following the idea that using:</p>
  
  <pre><code> MethodInfo.Invoke
  </code></pre>
  
  <p>Is nothing performative ( <a href="https://stackoverflow.com/questions/10820453/reflection-performance-create-delegate-properties-c">Reflection Performance - Create Delegate (Properties C#)</a>)
  I would like to translate any call to methods. I thought of something that would work like this:</p>
  
  <pre><code>public static T Create&lt;T&gt;(Type type, string methodName) // or
  public static T Create&lt;T&gt;(MethodInfo info) // to use like this:
  var action = Create&lt;Action&lt;object&gt;&gt;(typeof(Foo), "AnySetValue");
  </code></pre>
  
  <p>One requirement is that all the parameters, can be object.</p>
  
  <p>I'm trying to deal with expressions, and so far I have something like this:</p>
  
  <pre><code>    private void Sample()
      {
          var assembly = Assembly.GetAssembly(typeof(Foo));
  
          Type customType = assembly.GetType("Foo");
  
          var actionMethodInfo = customType.GetMethod("AnyMethod");
          var funcMethodInfo = customType.GetMethod("AnyGetString");
          var otherActionMethod = customType.GetMethod("AnySetValue");
          var otherFuncMethodInfo = customType.GetMethod("OtherGetString");
  
          var foo = Activator.CreateInstance(customType);
          var actionAccessor = (Action&lt;object&gt;)BuildSimpleAction(actionMethodInfo);
          actionAccessor(foo);
  
          var otherAction = (Action&lt;object, object&gt;)BuildOtherAction(otherActionMethod);
          otherAction(foo, string.Empty);
  
          var otherFuncAccessor = (Func&lt;object, object&gt;)BuildFuncAccessor(funcMethodInfo);
          otherFuncAccessor(foo);
  
          var funcAccessor = (Func&lt;object,object,object&gt;)BuildOtherFuncAccessor(otherFuncMethodInfo);
          funcAccessor(foo, string.Empty);
      }
  
      static Action&lt;object&gt; BuildSimpleAction(MethodInfo method)
      {
          var obj = Expression.Parameter(typeof(object), "o");
  
          Expression&lt;Action&lt;object&gt;&gt; expr =
              Expression.Lambda&lt;Action&lt;object&gt;&gt;(
                  Expression.Call(
                      Expression.Convert(obj, method.DeclaringType),
                      method), obj);
  
          return expr.Compile();
      }
  
      static Func&lt;object, object&gt; BuildFuncAccessor(MethodInfo method)
      {
          var obj = Expression.Parameter(typeof(object), "o");
  
          Expression&lt;Func&lt;object, object&gt;&gt; expr =
              Expression.Lambda&lt;Func&lt;object, object&gt;&gt;(
                  Expression.Convert(
                      Expression.Call(
                          Expression.Convert(obj, method.DeclaringType),
                          method),
                      typeof(object)),
                  obj);
  
          return expr.Compile();
  
      }
  
      static Func&lt;object, object, object&gt; BuildOtherFuncAccessor(MethodInfo method)
      {
          var obj = Expression.Parameter(typeof(object), "o");
          var value = Expression.Parameter(typeof(object));
  
          Expression&lt;Func&lt;object, object, object&gt;&gt; expr =
              Expression.Lambda&lt;Func&lt;object, object, object&gt;&gt;(
                      Expression.Call(
                          Expression.Convert(obj, method.DeclaringType),
                          method,
                          Expression.Convert(value, method.GetParameters()[0].ParameterType)), 
                          obj, value);
  
          return expr.Compile();
  
      }
  
      static Action&lt;object, object&gt; BuildOtherAction(MethodInfo method)
      {
          var obj = Expression.Parameter(typeof(object), "o");
          var value = Expression.Parameter(typeof(object));
  
          Expression&lt;Action&lt;object, object&gt;&gt; expr =
              Expression.Lambda&lt;Action&lt;object, object&gt;&gt;(
                  Expression.Call(
                      Expression.Convert(obj, method.DeclaringType),
                      method,
                      Expression.Convert(value, method.GetParameters()[0].ParameterType)),
                  obj,
                  value);
  
          return expr.Compile();
      }
  </code></pre>
  
  <hr>
  
  <pre><code>public class Foo
  {
      public void AnyMethod() {}
  
      public void AnySetValue(string value) {}
  
      public string AnyGetString()
      {            return string.Empty;        }
  
      public string OtherGetString(string value)
      {            return string.Empty;        }
  }
  </code></pre>
  
  <p>Is there any way to simplify this code? (I believe it is possible to create a method only using generic..) And when you have 3, 4, 5, any parameters as I do?</p>
  
  <hr>
  
  <p>I was thinking, what if there was something like this:</p>
  
  <p><a href="https://codereview.stackexchange.com/questions/1070/generic-advanced-delegate-createdelegate-using-expression-trees">https://codereview.stackexchange.com/questions/1070/generic-advanced-delegate-createdelegate-using-expression-trees</a></p>
  
  <p>but I'll have more one parameter (in action or function), this parameter (first parameter) an object to perform.
  Is this possible?</p>