반사. 일반 기본 클래스 일반 메소드 호출
-
05-07-2019 - |
문제
나는 일반적인 방법이있는 일반 유형 (계약을 채우기)을 동적으로 하위 분류하고 있습니다. 나는이 일반적인 방법을 호출하려고하지만 내가 생산하는 어셈블리에는 오류가 있습니다. 어셈블리를 열 때 반사판 충돌이 발생 하며이 코드 스 니펫은 실행되지 않습니다.
내가 얻는 예외는 다음과 같습니다.
잘못된 형식의 프로그램을로드하려고 시도했습니다. (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[] { });
}
}
해결책
대신에:
var testGeneric = testClass
.GetMethod("TestMethod")
.MakeGenericMethod(typeof(int));
필요 :
var testGeneric = testClassOfObject
.GetMethod("TestMethod")
.MakeGenericMethod(typeof(int));
왜냐하면 testClass
개방형 일반 클래스 유형이며 메소드를 호출하려고하면 충돌이 발생합니다.
제휴하지 않습니다 StackOverflow