今天我发现了一件有趣的事情。我尝试使用TypeBuilder
动态定义类型,并尝试"覆盖"(即替换)在基类中定义的方法:
public class Test
{
public void Method()
{
Console.WriteLine("Test from Test");
}
}
public void Bind(string methodToReplace, Action expr)
{
@object = Activator.CreateInstance<T>();
Type objectType = @object.GetType();
AssemblyBuilder asmBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(new AssemblyName("Mock"), AssemblyBuilderAccess.Run);
ModuleBuilder modBuilder = asmBuilder.DefineDynamicModule("Mock");
TypeBuilder tB = modBuilder.DefineType(objectType.Name, TypeAttributes.Public | TypeAttributes.Class, objectType);
var mB = tB.DefineMethod(methodToReplace, MethodAttributes.Public);
ILGenerator ilGen = mB.GetILGenerator();
ilGen.EmitCall(OpCodes.Call, expr.GetType().GetMethod("Invoke"), null);
ilGen.Emit(OpCodes.Ret);
@object = (T)Activator.CreateInstance(tB.CreateType());
}
但是,不幸的是,在定义的类型中有两个方法具有相同的名称'Method' ('t'是动态定义类型的实例):
t.GetType().GetMethods()
{System.Reflection.MethodInfo[6]}
[0]: {Void Method()}
[1]: {Void Method()}
[2]: {System.String ToString()}
[3]: {Boolean Equals(System.Object)}
[4]: {Int32 GetHashCode()}
[5]: {System.Type GetType()}
所以我的问题是:如何添加一个隐藏基类实现的新方法,相当于在定义新方法时使用c#的"new"关键字,例如:
public class Test2 : Test
{
new public void Method()
{
}
}
您可以看到两个方法,因为您使用了type.GetMethods()而没有使用bindingflags。尝试使用bindingflags. declardonly .
只能看到一个方法。这正是你想做的。
new关键字是c#中用来避免错误隐藏基方法的。
它强制您使用override或new来避免警告。
如果你想重写基方法,在TypeBuilder上使用DefineMethodOverride方法