代码之家  ›  专栏  ›  技术社区  ›  Jianhui Wang

返回泛型参数T并返回收益率

  •  1
  • Jianhui Wang  · 技术社区  · 7 年前

    我想从加载的dll文件生成一个类型列表(从T类继承)。但当我使用以下代码时,应用程序会冻结/卡住:

    static IEnumerable<T> GetAllTypes<T>(string dllName)
    {
        Assembly plugin = Assembly.LoadFrom(dllName);
        if (plugin != null)
        {
            Type[] types = plugin.GetTypes();
            foreach (var type in types)
            {
                if (type.IsClass && type.IsSubclassOf(typeof(T)))
                {
                    Console.WriteLine(type.Name);
                    yield return (T)(Object)type;
                }
            }
        }
        else
            throw new InvalidDataException();
    }
    

    然而,如果我不使用收益率回报,一切都会按预期进行,不会发生冻结。有人能解释这种行为吗?

    static void GetAllTypes<T>(string dllName)
    {
        Assembly plugin = Assembly.LoadFrom(dllName);
        if (plugin != null)
        {
            Type[] types = plugin.GetTypes();
            foreach (var type in types)
            {
                if (type.IsClass && type.IsSubclassOf(typeof(T)))
                {
                    Console.WriteLine(type.Name);
                    //yield return (T)(Object)type;
                }
            }
        }
        else
            throw new InvalidDataException();
    }
    
    2 回复  |  直到 7 年前
        1
  •  0
  •   Peter B    7 年前

    请注意 type 是一个 的实例 System.Type 。你应该把它退回,然后 IEnumerable<System.Type> 返回类型。

    类型转换代码尝试将该对象转换为 的实例 T 这是无效的,不可能的,它永远不会起作用。类型T的对象与类型T本身不同,但这正是您的代码试图强制的。

    不确定是否会导致“挂起”,但演员代码是错误的。

        2
  •  0
  •   InBetween    7 年前

    您的应用程序可能没有卡住,问题是迭代器 懒惰的 。你已经提出了一个问题,但实际上还没有提出。

    var types = GetTypes("Foo");
    

    这只会创建一个查询,但实际上不会执行它。这将:

    foreach (var t in types) { ... }
    

    也就是说,您的代码永远不会像其他答案中所解释的那样工作。 typeof(T) 和a T 是完全不同的事情。