包含c#中列表的动态类型

Sti*_*ahl 4 c# types dynamic

我有一点问题.

我想这样做:

Type[] classes = new Type[]{ Class1, Class2 };

foreach(Type t in classes){   
  List<t> list = new List<t>(); 
}
Run Code Online (Sandbox Code Playgroud)

有办法做到这一点吗?

Ada*_*rth 6

不能在运行时转换为泛型类型,因为泛型中的类型需要在编译时解析.

可以使用反射以动态方式创建泛型类型,但除非您对强制转换进行硬编码,否则您获得的所有内容都是对象.

我不能真正说出你想要的是什么,我不得不同意这是一个XY问题.我倾向于做出这样一种冒昧的陈述:这是一个设计问题,它试图解决,而不是直接解决设计问题,或者询问你想要直接实现的问题.


您可以使用以下代码创建类型,然后该dynamic类型可用于在不知道/关心它是列表或什么是以下内容的情况下对各种成员进行类型化:List<T>T

using System;
using System.Collections.Generic;

namespace ConsoleApplication61
{
    class Program
    {
        static void Main(string[] args)
        {
            dynamic o = CreateGeneric(typeof(List<>), typeof(int));
            o.Add(1);
            Console.WriteLine(o[0]);
            Console.Read();
        }

        public static object CreateGeneric(Type generic, Type innerType, params object[] args)
        {
            System.Type specificType = generic.MakeGenericType(new System.Type[] { innerType });
            return Activator.CreateInstance(specificType, args);
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

上面的示例duck类型Add方法和Indexer.DLR在运行时进行类型处理和鸭子类型化 - 例如,知道它1是一个int.

只是为了澄清,我可能不会在生产中使用这样的代码(除非你的要求非常具体需要这个),并且任何类型不匹配的问题都会在运行时发生; 因此您需要非常准确地键入(有限的IntelliSense)或具有良好的错误处理.

感谢此博客文章CreateGeneric方法.

这假定.NET 4具有新的CLR.正如@MartinLiversage也指出的那样,这个特定的示例假设您以强类型的方式使用列表.在我的例子中,我传递intList<int>隐藏在一个dynamic.


自从它发布以来,我们一直在使用.NET 4.我们有一个大型应用程序,具有更大的代码库.dynamic在应用程序中不使用一次,在测试代码库中只使用几次.这并不是说"不要使用它",而是说"大多数时候,你不需要它".


Erw*_*win 5

你可以这样做:

foreach(Type t in classes)
{
   var listType = typeof(List<>).MakeGenericType(t);
   var instance = Activator.CreateInstance(listType);
}
Run Code Online (Sandbox Code Playgroud)

  • Activator.CreateInstance将返回一个对象,如何在运行时强制转换它以获得对`t`的强类型访问? (3认同)