Как я могу использовать дерево выражений для вызова универсального метода, когда тип известен только во время выполнения?

Это то, что я решил с помощью отражения, но хотел бы посмотреть, как это сделать, используя деревья выражений.

У меня есть общая функция:

private void DoSomeThing( param object[] args ) { // Some work is done here. } 

что мне нужно позвонить из другого места в моем classе. Теперь, как правило, это было бы просто:

 DoSomeThing( blah ); 

но только если я знаю, что во время разработки я работаю с int . Когда я не знаю тип до тех пор, пока время выполнения не понадобится мне. Как я уже сказал, я знаю, как это сделать с помощью рефлексии, но я хотел бы сделать это через деревья выражений, поскольку мое (очень ограниченное) понимание заключается в том, что я могу это сделать.

Любые предложения или точки на сайтах, где я могу получить это понимание, желательно с образцом кода?

MethodInfo.MakeGenericMethod

Затем просто создайте делегат и вызовите его. (не в выражении, конечно, p)

Обновить:

Как правило, я предпочитаю использовать для этого общие типы, Activator.CreateInstance просто требует меньше работы. Все зависит от вашей ситуации.

Да, это можно сделать с помощью деревьев выражений. Преимущество состоит в том, что вы получаете делегата, поэтому повторные вызовы будут намного быстрее, чем повторение MethodInfo.Invoke() снова и снова. Это может также помочь dynamic ключевое слово.

Пример:

 What type would you like to use? decimal Selected type 'System.Decimal' Input Value: 5.47 <<>> The object has static type 'System.Object', dynamic type 'System.Decimal', and value '5.47' <<>> The object has static type 'System.Decimal', dynamic type 'System.Decimal', and value '5.47' <<>> The object has static type 'System.Decimal', dynamic type 'System.Decimal', and value '5.47' <<>> The object has static type 'System.Decimal', dynamic type 'System.Decimal', and value '5.47' 

Код:

 using System; using System.ComponentModel; using System.Linq; using System.Linq.Expressions; using System.Reflection; namespace SO2433436 { class Program { static void LogObject(T t) { Console.WriteLine("The object has static type '" + typeof(T).FullName + "', dynamic type '" + t.GetType() + "', and value '" + t.ToString() + "'"); } static void Main(string[] args) { Console.WriteLine("What type would you like to use?"); string typeName = Console.ReadLine(); Type userType; switch (typeName) { case "byte": userType = typeof(byte); break; case "sbyte": userType = typeof(sbyte); break; case "ushort": userType = typeof(ushort); break; case "short": userType = typeof(short); break; case "uint": userType = typeof(uint); break; case "int": userType = typeof(int); break; case "string": userType = typeof(string); break; case "decimal": userType = typeof(decimal); break; default: userType = Type.GetType(typeName); break; } Console.WriteLine("Selected type '" + userType.ToString() + "'"); Console.WriteLine("Input Value:"); string val = Console.ReadLine(); object o = TypeDescriptor.GetConverter(userType).ConvertFrom(val); Console.WriteLine("<<>>"); LogObject(o); Console.WriteLine("<<>>"); LogObject((dynamic)o); Console.WriteLine("<<>>"); Action f = LogObject; MethodInfo logger = f.Method.GetGenericMethodDefinition().MakeGenericMethod(userType); logger.Invoke(null, new[] { o }); Console.WriteLine("<<>>"); var p = new[] { Expression.Parameter(typeof(object)) }; Expression> e = Expression.Lambda>( Expression.Call(null, logger, Expression.Convert(p[0], userType) ) , p); Action a = e.Compile(); a(o); } } }