我可以在运行时将类中的字段类型设置为c#中新创建的类型吗?

时间:2016-02-08 01:06:11

标签: c# reflection casting reflection.emit typebuilder

我正在使用Reflection.EmitTypeBuilder在运行时创建新类型。我的设置类似于:

public class MyClass {
    public object MyField = CreateInstanceOfNewType();
    public MyClass() {}
}

问题是MyClass.MyField是使用类型object声明的,因此当将可转换类型分配给MyClass.MyField时,不会调用新类型存在的隐式转换运算符。有没有办法将字段类型设置为新创建的类型,以便它的行为与典型情况下的行为类似?

2 个答案:

答案 0 :(得分:1)

这取决于确切的用例,可能的解决方案是使您的类具有通用性,然后使用反射创建一个静态泛型方法来创建该类的实例。这允许您在声明属性时使用变量动态类型:

public class MyClass<T> { 
public T MyField = CreateInstanceOfNewType<T≥(); 
public MyClass() {} 
}

public static MyClass<T> createClass<T>() {
return new MyClass<T>:
}

dynamic instanceOfMyClass = typeof(SomeClass).GetMethod("createClass").MakeGeneric(dynamicType).Invoke()

另一种选择是使用动态关键字。

答案 1 :(得分:0)

如果我理解正确,你想要初始化一个新类型的对象,你有一个可铸造类型的对象,你已经构建了一个隐式的强制转换操作符。我建议您使用构造函数而不是隐式运算符:使用Reflection.Emit创建构造函数,该构造函数接受可转换类型的一个参数,并使用该参数值初始化新类型的对象。您希望获得与此代码段相同的结果:

public class MyNewType
{
    public MyNewType(CastableType value)
    {
        /* implement initialization with value */
    }

    /* other stuff */
}

然后,您可以使用Activator.CreateInstance(Type type, params object[] arguments)来使用该构造函数。这是一个例子:

var newType = GetNewType();
var castableObject = CreateInstanceOfCastableType();
this.MyField = Activator.CreateInstance(newType, castableObject);