2009-09-10 48 views
3

我動態地分類泛型類型(填充它的合同),它具有通用方法。我試圖調用這個通用方法,但是我生成的程序集有錯誤。試圖打開程序集時,Reflector會崩潰,並且此代碼段不能運行。Reflection.Emit通用基類通用方法調用

我得到的例外是:

試圖加載程序格式不正確。 (異常來自HRESULT:0x8007000B)

任何幫助,將不勝感激。我將安裝PEVerify來查看生成的代碼。

using System; 
using System.Reflection; 
using System.Reflection.Emit; 

public class TestClass<TFirst> 
{ 
    public void TestMethod<TSecond>() 
    { 
     Console.WriteLine("It works"); 
    } 
} 
public class Program 
{ 
    static void Main(string[] args) 
    { 
     // create a dynamic assembly and module 
     var assemblyName = new AssemblyName("DynamicAssembly"); 
     var assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); 
     var module = assemblyBuilder.DefineDynamicModule("DynamicAssembly.dll"); 

     // public class Voodoo.Dynamic.Class : TestClass<object> 
     var testClass = typeof(TestClass<>); 
     var testClassOfObject = testClass.MakeGenericType(typeof(object)); 
     var typeBuilder = module.DefineType(
      "Voodoo.Dynamic.Class", 
      TypeAttributes.Public | TypeAttributes.Class, 
      testClassOfObject); 

     // public void Run() 
     var methodBuilder = typeBuilder.DefineMethod("Run", MethodAttributes.Public); 

     // this.TestMethod<int>(); 
     var testGeneric = testClass.GetMethod("TestMethod").MakeGenericMethod(typeof(int)); 
     var il = methodBuilder.GetILGenerator(); 
     il.Emit(OpCodes.Ldarg_0); // load this 
     il.Emit(OpCodes.Call, testGeneric); 
     il.Emit(OpCodes.Ret); 

     // bake it 
     var classType = typeBuilder.CreateType(); 

     assemblyBuilder.Save("DynamicAssembly.dll"); 

     // var instance = new Voodoo.Dynamic.Class(); 
     var instance = Activator.CreateInstance(classType); 

     // instance.Run(); 
     classType.GetMethod("Run").Invoke(instance, new object[] { }); 
    } 
} 

回答

6

相反的:

var testGeneric = testClass 
    .GetMethod("TestMethod") 
    .MakeGenericMethod(typeof(int)); 

您需要:

var testGeneric = testClassOfObject 
    .GetMethod("TestMethod") 
    .MakeGenericMethod(typeof(int)); 

因爲testClass是一個開放式泛型類的類型,如果你嘗試調用的方法就會崩潰。

+0

乾杯,這個答案讓我解決了更復雜的問題。該項目仍然無法正常工作,但我距離更近。 – 2009-09-10 21:53:35