System.Reflection.Emit的一个很重要的发现.
在同一个ModuleBuilder里, DefineType并且CreateType之后, 是可以继续DefineType的..
这样可以防止编译多次代码导致的AssemblyBuilder过多的问题. 现在只需要1个AssemblyBuilder就够了.
这个发现对于WEB框架非常有意义. 因为WEB框架包含大量的脚本文件. 有了这个特征, 脚本文件可以很放心地分开来编译了
using System;
using System.Collections.Generic;
using System.Text;
using System.Reflection;
using System.Reflection.Emit;
static public class EmitTest
{
static public void Go()
{
AssemblyBuilder asm = AppDomain.CurrentDomain.DefineDynamicAssembly(
new AssemblyName("EmitTest"), AssemblyBuilderAccess.Run);
ModuleBuilder mdl=asm.DefineDynamicModule("EmitTestModule");
RunType(mdl, "Type1", "Method1", "Hello");
RunType(mdl, "Type2", "Method2", "World");
}
private static void RunType(ModuleBuilder mdl,string typename
,string methodname,string writestring)
{
TypeBuilder t1 = mdl.DefineType(typename);
MethodBuilder mb1 = t1.DefineMethod(methodname
, MethodAttributes.Static | MethodAttributes.Public, typeof(void), new Type[] { });
ILGenerator g1 = mb1.GetILGenerator();
g1.Emit(OpCodes.Ldstr, writestring);
g1.Emit(OpCodes.Call, typeof(EmitTest).GetMethod("WriteLine"));
MethodInfo mi1 = t1.CreateType().GetMethod(methodname);
mi1.Invoke(null, null);
}
[System.Runtime.CompilerServices.MethodImpl(
System.Runtime.CompilerServices.MethodImplOptions.NoInlining)]
static public void WriteLine(string str)
{
MethodBase caller=new System.Diagnostics.StackFrame(1).GetMethod();
Console.WriteLine(caller.DeclaringType.Assembly.FullName);
Console.WriteLine(str);
}
}
                    
                
                
            
        
浙公网安备 33010602011771号