【发布时间】:2013-08-30 07:21:46
【问题描述】:
我正在尝试基于仅包含公共字段的现有类型创建动态类型。新的动态类型还必须继承自仅具有完全实现的方法的不同基类型。
我创建TypeBuilder 指定基本类型,然后向其中添加公共字段,最后调用CreateType()。产生的错误信息是:
“无法从程序集“MyDynamicAssembly”加载类型“InternalType”, 版本=0.0.0.0,文化=中性,PublicKeyToken=null' 因为字段 'first' 没有给出明确的偏移量。”
对我来说,这意味着CreateType 方法正在寻找基类中的“first”公共字段,这是一个问题,因为它不存在。为什么它认为添加的字段应该在基类中?或者,我是否误解了异常?
代码如下:
public class sourceClass
{
public Int32 first = 1;
public Int32 second = 2;
public Int32 third = 3;
}
public static class MyConvert
{
public static object ToDynamic(object sourceObject, out Type outType)
{
// get the public fields from the source object
FieldInfo[] sourceFields = sourceObject.GetType().GetFields();
// get a dynamic TypeBuilder and inherit from the base type
AssemblyName assemblyName
= new AssemblyName("MyDynamicAssembly");
AssemblyBuilder assemblyBuilder
= AppDomain.CurrentDomain.DefineDynamicAssembly(
assemblyName,
AssemblyBuilderAccess.Run);
ModuleBuilder moduleBuilder
= assemblyBuilder.DefineDynamicModule("MyDynamicModule");
TypeBuilder typeBuilder
= moduleBuilder.DefineType(
"InternalType",
TypeAttributes.Public
| TypeAttributes.Class
| TypeAttributes.AutoClass
| TypeAttributes.AnsiClass
| TypeAttributes.ExplicitLayout,
typeof(SomeOtherNamespace.MyBase));
// add public fields to match the source object
foreach (FieldInfo sourceField in sourceFields)
{
FieldBuilder fieldBuilder
= typeBuilder.DefineField(
sourceField.Name,
sourceField.FieldType,
FieldAttributes.Public);
}
// THIS IS WHERE THE EXCEPTION OCCURS
// create the dynamic class
Type dynamicType = typeBuilder.CreateType();
// create an instance of the class
object destObject = Activator.CreateInstance(dynamicType);
// copy the values of the public fields of the
// source object to the dynamic object
foreach (FieldInfo sourceField in sourceFields)
{
FieldInfo destField
= destObject.GetType().GetField(sourceField.Name);
destField.SetValue(
destObject,
sourceField.GetValue(sourceField));
}
// give the new class to the caller for casting purposes
outType = dynamicType;
// return the new object
return destObject;
}
【问题讨论】:
-
能否请您展示一下如何使用 ToDynamic(..) 方法?
-
感谢您提供这个非常好的主题。但是你不是用基类复制一个新类,而不是从基类继承吗?
标签: c# inheritance reflection reflection.emit typebuilder