【问题标题】:Can you instantiate a template class at runtime using C#您可以在运行时使用 C# 实例化模板类吗
【发布时间】:2012-11-22 12:33:24
【问题描述】:

是否可以在运行时实例化模板类,例如:

Type type = Type.GetType("iTry.Workflow.Person");
WorkflowPropertyViewModel<type> propViewModel = new WorkflowPropertyViewModel<type>();

这显然行不通。还有其他方法吗?

Generic 类如下所示:

public class WorkflowPropertyViewModel<T> : IProperty<T>  
{
    public Task<T> ValueAsync
    {
        get;
        set;
    }

    public T Value
    {
        get;
        set;
    }

    public IQueryable<T> PossibleItems
    {
        get;
        set;
    }
}

【问题讨论】:

    标签: c# templates generics runtime


    【解决方案1】:

    您可以在给定 Type 对象的情况下创建任何类型的对象:

    object o = Activator.CreateInstance(type);
    

    这假定该类型具有默认构造函数。传递构造函数参数还有其他 Activator 方法:

    http://msdn.microsoft.com/en-us/library/wccyzw83.aspx

    为了获得特定的泛型类型,您可以在泛型类型定义上调用 MakeGenericType

    http://msdn.microsoft.com/en-us/library/system.type.makegenerictype.aspx

    总而言之,它看起来像:

    var type = Type.GetType("iTry.Workflow.Person");
    var genericType = typeof(WorkflowPropertyViewModel<>).MakeGenericType(type);
    var o = Activator.CreateInstance(genericType);
    

    【讨论】:

    • 有趣的问题是:如何获得type?你应该用一个样本来回答这个问题。
    • 以及如何在运行时为模板提供类型
    • @tillerstarr:这就是MakeGenericType 的用途。顺便说一句:它是“通用”而不是“模板”。
    【解决方案2】:

    是的,您可以使用仅在运行时才知道的类型来实例化泛型类,例如:

    public class A { }
    public class U<T> {
        public T X { get; set; }
    }
    
    static void Main(string[] args) {
        Type a = typeof(A);
        Type u = typeof(U<>);
        dynamic uOfA = Activator.CreateInstance(u.MakeGenericType(a));
        uOfA.X = new A();
        Console.WriteLine(uOfA.GetType());
        Console.WriteLine(uOfA.X.GetType());
    }
    

    但是,这个 sn-p 使用反射和动态类型,这两者都可能导致很多维护问题,所以你最好小心使用它们或找到更简单的解决方案。

    【讨论】:

    • 感谢这对我有用。动态似乎可以完成工作。
    【解决方案3】:

    试试这个:

    object o = Activator.CreateInstance(typeof(WorkflowPropertyViewModel<>).MakeGenericType(new Type[] {type}));
    

    请注意,在代码中你不能轻易引用该类型,除非它实现了另一个非泛型接口 - 所以你必须使用 object 代替或使用更多反射。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-07-08
      • 2013-12-24
      • 2013-01-08
      • 1970-01-01
      • 1970-01-01
      • 2022-01-17
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多